home *** CD-ROM | disk | FTP | other *** search
- ;=1.06=;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; FunkLite - By Super Real Darwin! ;
- ; Designed & Coded By Jason Nunn (JsNO) ;
- ; ;
- ; The Playback routines.. ;
- ; ;
- ; Snail: 32 Rothdale Road, Moil, Darwin, NT, Australia ;
- ; Email: jsno@amigar.apana.org.au ;
- ; BBS : ■ Amiga Retreat BBS (3:850/105) ;
- ; (089)451516 ;
- ; ■ Sentinel BBS (SRD's base) ;
- ; (089)452708 ;
- ; ;
- ; ===================================================================== ;
- ; ;
- ; Funktracker processes sound exclusively in backround. Unlike many ;
- ; playback routines that require mixxer calls to be dotted through out ;
- ; ones code, funktracker processes music totally in backround without any ;
- ; foreground processing required. ;
- ; ;
- ; These is the attachment that contents all code necessary to play a FNK ;
- ; module. Refer to the EXAMPLE.ASM for a demo of how to use. ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Global ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ; Subjective quality Scale (on my Pentium)
- ;
- ; SHITHOUSE GOOD EXCELLENT
- ; │ │ │
- ;
- ; SB2.0│*******
- ; SBPRO│*********************
- ; GUS│************************************
- ; SB16│************************************************
- ; PAS16│************************************************
- ;
-
- SB_CARD = 0
- SBPRO_CARD = 1
- GUS_VARB_CARD = 2 ;<<---Channel panning can vary according to sample
- SB15EM_CARD = 3
- SB16_CARD = 4
- GUS_FIXB_CARD = 5 ;<<- fixed DAC/669 style left-right-left-right balances
- RIPPED_CARD = 6
- PAS16_CARD = 7
-
- struc tinit_settings
- header db "Funktracker config file. Don't edit this thing."
- card_type db ?
- PORT_no dd ?
- IRQ_no db ?
- DMA_no db ?
- IRQ_no2 db ?
- DMA_no2 db ?
- DAC_Samplerate db ?
- ends
- init_settings tinit_settings <>
-
- struc tDAC_ssetings ; these struc variables control the DMA
- DAC_sr dd ? ; a sample rate for each card. The idea
- DAC_mix_buffer_size dd ? ; is to maintain a 0.02 of a second
- DMA_length dd ? ; tick when processing DAC DMA transfers.
- DMA_real_sr dd ? ; both tracker and DAC mixxer run of the same interrupt.
- ends
-
- ;For your demo, change these memory requirements to your needs;;;;;;;;;;;;;;
- sample_memory_lim dd 200000h
- funk_pd_size = (600h*128)
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- file_handle_funk dd ?
- sample_block_size dd ?
- sequence_ofs_old db 0 ;for display purposes, if you are going
- pattern_ofs2_old db 0 ;to get the sequence or pattern ofs, then
- ;use these variables..
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Tracker Data ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Structures ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- STOP = 0
- PLAY = 1
-
- struc tfunk_hr
- sig dd ?
- info dd ?
- LZH_check_size dd ?
- LZH_check_sum dd ?
- loop_order db ? ; if FFh then no loop
- order_list db 256 dup(?)
- break_list db 128 dup(?)
- ends
-
- struc tfunk_sb
- sname db 19 dup(?)
- start dd ?
- length dd ?
- volume db ? ; (0 to FF)
- balance db ? ; (0 to FF)
- pt_and_sop db ?
- vv_waveform db ?
- rl_and_as db ?
- ends
-
- struc tfunk_chan
- ;─control system─────────────────
- channel_kill db PLAY
- command db ?
- com_val db ?
- comspd_count db ? ; crtl rapid speed delay
- sample db ? ; thenis serves no purpose
- start dd ?
- length dd ?
- funkctrl db ?
- port_type db ?
- sample_ofs_parm db ?
- vib_waveform db ?
- vol_vib_waveform db ?
- retrig_spd_count db ?
- retrig_count db ?
- retrig_limit db ?
- arp_speed db ?
- balance db ? ; 0 to 15
- ;─note system────────────────────
- note_command db ?
- note_com_val db ?
- note_comspd_count db ? ; note rapid speed delay
- note db ?
- ifreq dd ? ; real_freq = FACTOR / invert_freq
- ifreq_vibrato dd ? ; used by vibrato, tremola, freqadetc
- ifreq_portdest dd ? ; used by porta
- rfreq dd ? ; the real frequency
- rfreq_adjust dd ?
- rfreq_portdest dd ?
- vib_ptr db ?
- note_beat_count db ? ; used by arpeggio and retrig, fanin, fanout
- ;─volume system──────────────────
- volume_command db ?
- volume_com_val db ?
- volume_comspd_count db ? ; volume rapid speed delay
- volume db ?
- volume_vibrato db ?
- volume_portdest db ?
- rvolume db ?
- vol_vib_ptr db ?
- volume_beat_count db ? ; used by reverb, crest, though
- ;─card dependant─────────────────
- CARD_sample_ptr dd ?
- CARD_freq dd ?
- CARD_freq_attract dd ?
- CARD_volume dd ?
- ends
-
- struc tfunk_info
- trek_status db ?
- sequence_ofs db ?
- pattern_ofs db ?
- tempo db ?
- tempo_count db ?
- no_of_patterns db ?
- no_of_sequences db ?
- master_volume db ?
- sample_ptrs dd 64 dup(?)
- ends
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; var ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- note_table:
- dd 13696,12928,12192,11520,10848,10240, 9664, 9120, 8608, 8128, 7680
- dd 7248, 6848, 6464, 6096, 5760, 5424, 5120, 4832, 4560, 4304, 4064
- dd 3840, 3624, 3424, 3232, 3048, 2880, 2712, 2560, 2416, 2280, 2152
- dd 2032, 1920, 1808, 1712, 1616, 1520, 1440, 1360, 1280, 1208, 1144
- dd 1080, 1016, 960, 904, 856, 808, 760, 720, 680, 640, 600
- dd 568, 536, 504, 480, 448, 0, 0, 0, 0
- com_ifreq_inc:
- db 001,004,006,010,012,016,020,024
- db 031,047,063,083,107,139,187,251
- com_rfreq_inc:
- dd 00016,00032,00048,00064,00096,00128,00160,00192
- dd 00244,00255,00383,00511,00639,00767,00895,01024
- com_volume_inc:
- db 001,002,003,004,005,006,007,008
- db 010,012,016,020,024,032,048,064
-
- com_sine_table:
- db -6, -19, -31, -43, -55, -66, -76, -86
- db -95,-103,-110,-116,-120,-124,-127,-128
- db -128,-127,-124,-121,-116,-110,-103, -95
- db -86, -77, -66, -55, -44, -32, -19, -7
- db 6, 18, 30, 42, 54, 65, 76, 85
- db 94, 102, 109, 115, 120, 124, 126, 127
- db 127, 126, 124, 121, 116, 110, 104, 96
- db 87, 77, 67, 56, 44, 32, 20, 8
- com_triangle_table:
- db -4, -12, -20, -28, -36, -44, -52, -60
- db -68, -76, -84, -92,-100,-108,-116,-124
- db -124,-116,-108,-100, -92, -84, -76, -68
- db -60, -52, -44, -36, -28, -20, -12, -4
- db 4, 12, 20, 28, 36, 44, 52, 60
- db 68, 76, 84, 92, 100, 108, 116, 124
- db 123, 115, 107, 99, 91, 83, 75, 67
- db 59, 51, 43, 35, 27, 19, 11, 3
- com_square_table:
- db -064,-128,-128,-127,-127,-128,-128,-127
- db -127,-128,-128,-127,-127,-128,-128,-127
- db -127,-128,-128,-127,-127,-128,-128,-127
- db -127,-128,-128,-127,-127,-128,-128,-064
- db 095, 127, 127, 126, 126, 127, 127, 126
- db 126, 127, 127, 126, 126, 127, 127, 126
- db 126, 127, 127, 126, 126, 127, 127, 126
- db 126, 127, 127, 126, 126, 127, 127, 095
- com_sawtooth_table:
- db -1, -5, -9, -13, -17, -21, -25, -29
- db -33, -37, -41, -45, -49, -53, -57, -61
- db -65, -69, -73, -77, -81, -85, -89, -93
- db -97,-101,-105,-109,-113,-117,-121,-125
- db 127, 123, 119, 115, 111, 107, 103, 99
- db 95, 91, 87, 83, 79, 75, 71, 67
- db 63, 59, 55, 51, 47, 43, 39, 35
- db 31, 27, 23, 19, 15, 11, 7, 3
- com_random_table:
- db 168, 167, 167, 165, 201, 201, 202, 201
- db 244, 244, 244, 244, 85, 82, 85, 85
- db 44, 44, 44, 44, 114, 114, 114, 114
- db 77, 77, 73, 77, 116, 116, 116, 116
- db 87, 87, 87, 87, 31, 31, 31, 31
- db 198, 198, 198, 198, 105, 104, 105, 105
- db 103, 105, 103, 103, 166, 166, 165, 166
- db 171, 172, 171, 171, 217, 217, 217, 217
-
- funk_info tfunk_info <>
- funk_chan1 tfunk_chan <>
- funk_chan2 tfunk_chan <>
- funk_chan3 tfunk_chan <>
- funk_chan4 tfunk_chan <>
- funk_chan5 tfunk_chan <>
- funk_chan6 tfunk_chan <>
- funk_chan7 tfunk_chan <>
- funk_chan8 tfunk_chan <>
-
- CARD_freq_convert dd ?
- CARD_volume_convert dd ?
-
- funk_hr tfunk_hr <>
- funk_sb tfunk_sb 64 dup(<>)
- funk_pd_ptr dd ?
- funk_sd_ptr dd ?
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Tracker Code ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; ebx = ifreq, returns = eax ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc ifreq_to_rfreq_vib
- add ebx,[dword edi+tfunk_chan.ifreq_vibrato]
- js @@zero
- jz @@zero
- jmp @@set_r
- @@zero:
- mov ebx,1
- @@set_r:
- proc ifreq_to_rfreq
- xor edx,edx
- mov eax,1b4f4d0h
- div ebx
- add eax,[dword edi+tfunk_chan.rfreq_adjust] ; add 669 freq adjustment
- ret
- endp
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc vol_to_realvol
- mov bl,[byte edi+tfunk_chan.volume]
- mov [byte edi+tfunk_chan.rvolume],bl
- ret
- endp
-
- proc vol_to_realvol_vib
- movzx ebx,[byte edi+tfunk_chan.volume]
- add ebx,1000
- movzx eax,[byte edi+tfunk_chan.volume_vibrato]
- or al,al
- js @@sub
- add ebx,eax
- cmp ebx,1000+0ffh
- ja @@adjust_add
- jmp @@done
- @@adjust_add:
- mov ebx,1000+0ffh
- jmp @@done
- @@sub:
- neg al
- sub ebx,eax
- cmp ebx,1000
- jb @@adjust_sub
- jmp @@done
- @@adjust_sub:
- mov ebx,1000
- @@done:
- sub ebx,1000
- mov [byte edi+tfunk_chan.rvolume],bl
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; bl = note, returns bx = ifreq ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- macro @note_2_ifreq
- and ebx,111111b
- lea ebx,[ebx*4]
- mov ebx,[dword ebx+note_table]
- endm
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; misc. vibrato function used by ;
- ; frequency and volume functions ;
- ; ;
- ; al = waveform ;
- ; ah = amplitude ;
- ; cl = speed ;
- ; ebx = ptr to vibrato table ;
- ; returns al = value, ebx = ptr ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vib_func
- inc ah
- cmp al,1
- je @@vib_triangle
- cmp al,2
- je @@vib_square
- cmp al,3
- je @@vib_sawtooth
- cmp al,4
- je @@vib_random
- @@vib_sine:
- mov al,[byte ebx+com_sine_table]
- jmp @@get_func_value
- @@vib_triangle:
- mov al,[byte ebx+com_triangle_table]
- jmp @@get_func_value
- @@vib_square:
- mov al,[byte ebx+com_square_table]
- jmp @@get_func_value
- @@vib_sawtooth:
- mov al,[byte ebx+com_sawtooth_table]
- jmp @@get_func_value
- @@vib_random:
- mov al,[byte ebx+com_random_table]
- @@get_func_value:
- imul ah
- shr eax,4
- not cl
- and cl,1111b
- add bl,cl
- inc bl
- and bl,111111b
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; for NOTE 3D: reload samples ;
- ; attributes ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc reload_sample_attr
- movzx eax,[word esi] ;extract sample no
- xchg al,ah
- shr eax,4
- and eax,03fh
- mov [byte edi+tfunk_chan.sample],al
- movzx eax,al
- shl eax,5
- add eax,offset funk_sb
- proc reload_sample2
- mov bl,[byte eax+tfunk_sb.balance] ; get balance
- mov [byte edi+tfunk_chan.balance],bl
- mov bl,[byte eax+tfunk_sb.pt_and_sop] ; get both port type and sample ofs parm
- mov dl,bl
- shr bl,4
- and dl,1111b
- mov [byte edi+tfunk_chan.port_type],bl
- mov [byte edi+tfunk_chan.sample_ofs_parm],dl
- mov bl,[byte eax+tfunk_sb.vv_waveform] ; get both vibrato wf & tremola wf
- mov dl,bl
- shr bl,4
- and dl,1111b
- mov [byte edi+tfunk_chan.vib_waveform],bl
- mov [byte edi+tfunk_chan.vol_vib_waveform],dl
- mov bl,[byte eax+tfunk_sb.rl_and_as] ; get both retrig speed & arp speed
- mov dl,bl
- shr bl,4
- and dl,1111b
- mov [byte edi+tfunk_chan.retrig_limit],bl
- mov [byte edi+tfunk_chan.arp_speed],dl
- mov dl,[byte eax+tfunk_sb.volume]
- ret
- endp
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc decode_sample
- movzx eax,[word esi] ;extract sample no
- xchg al,ah
- shr eax,4
- and eax,03fh
- mov [byte edi+tfunk_chan.sample],al
- proc do_retrig_sample
- movzx eax,al
- push eax
- shl eax,5
- add eax,offset funk_sb
-
- mov [byte edi+tfunk_chan.funkctrl],10b ; set funkctrl
- mov ebx,[dword eax+tfunk_sb.start]
- cmp ebx,0ffffffffh
- je @@dont_loop
- mov [byte edi+tfunk_chan.funkctrl],11b ; set funkctrl
- @@dont_loop:
- mov [dword edi+tfunk_chan.start],ebx
- mov ebx,[dword eax+tfunk_sb.length]
- mov [dword edi+tfunk_chan.length],ebx
- call reload_sample2
- pop eax
- lea eax,[eax*4]
- mov eax,[dword eax+funk_info.sample_ptrs]
- add [dword edi+tfunk_chan.start],eax
- add [dword edi+tfunk_chan.length],eax
- mov [dword edi+tfunk_chan.CARD_sample_ptr],eax
- ret
- endp
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc do_full_note
- mov [byte edi+tfunk_chan.note],bl
- mov bl,[byte edi+tfunk_chan.note]
- mov [byte edi+tfunk_chan.volume],dl
- @note_2_ifreq
- mov [dword edi+tfunk_chan.ifreq],ebx
- call ifreq_to_rfreq
- mov [dword edi+tfunk_chan.rfreq],eax
- call vol_to_realvol
- call [dword CARD_freq_convert]
- call [dword CARD_volume_convert]
- ret
- endp
-
- proc load_attr_active
- mov [byte edi+tfunk_chan.volume],dl
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- endp
-
- proc normal_decode_system
- mov bl,[byte esi] ;extract note value
- shr bl,2
- cmp bl,3dh ; of ReLOad samples then ...
- je @@ReLOad_samples
- push ebx
- call decode_sample
- pop ebx
- cmp bl,3eh ; of SAMPLE ONLY slot
- je @@no_note_change ; then dont change note
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [byte edi+tfunk_chan.volume_command],0fh
- call do_full_note
- @@no_note_change:
- ret
- @@ReLOad_samples:
- call reload_sample_attr
- call load_attr_active
- ret
- endp
-
- proc normal_decode_note
- mov bl,[byte esi] ;extract note value
- shr bl,2
- cmp bl,3dh ; of ReLOad samples then ...
- je @@ReLOad_samples
- push ebx
- call decode_sample
- pop ebx
- cmp bl,3eh ; of SAMPLE ONLY slot
- je @@no_note_change ; then dont change note
- mov [byte edi+tfunk_chan.volume_command],0fh
- call do_full_note
- @@no_note_change:
- ret
- @@ReLOad_samples:
- call reload_sample_attr
- call load_attr_active
- ret
- endp
-
- proc normal_decode_volume
- mov bl,[byte esi] ;extract note value
- shr bl,2
- cmp bl,3dh ; of ReLOad samples then ...
- je @@ReLOad_samples
- push ebx
- call decode_sample
- pop ebx
- cmp bl,3eh ; of SAMPLE ONLY slot
- je @@no_note_change ; then dont change note
- mov [byte edi+tfunk_chan.note_command],0fh
- call do_full_note
- @@no_note_change:
- ret
- @@ReLOad_samples:
- call reload_sample_attr
- call load_attr_active
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc comc_decode
- mov bl,[byte esi] ;extract note value
- shr bl,2
- cmp bl,3dh ; of ReLOad samples then ...
- je @@ReLOad_samples
- push ebx
- call decode_sample
- pop ebx
- cmp bl,3eh ; of SAMPLE ONLY slot
- je @@cc_no_note_change ; then dont change note
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],dl
- mov [byte edi+tfunk_chan.note],bl
- @note_2_ifreq
- mov [dword edi+tfunk_chan.ifreq_portdest],ebx
- call ifreq_to_rfreq
- mov [dword edi+tfunk_chan.rfreq_portdest],eax
- call vol_to_realvol
- call [dword CARD_freq_convert]
- call [dword CARD_volume_convert]
- @@cc_no_note_change:
- ret
- @@ReLOad_samples:
- call reload_sample_attr
- call load_attr_active
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc comi_decode
- mov bl,[byte esi] ;extract note value
- shr bl,2
- cmp bl,3dh ; of ReLOad samples then ...
- je @@ReLOad_samples
- push ebx
- call decode_sample
- pop ebx
- cmp bl,3eh ; of SAMPLE ONLY slot
- je @@no_note_change ; then dont change note
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [byte edi+tfunk_chan.volume_portdest],dl
- mov [byte edi+tfunk_chan.note],bl
- @note_2_ifreq
- mov [dword edi+tfunk_chan.ifreq],ebx
- call ifreq_to_rfreq
- mov [dword edi+tfunk_chan.rfreq],eax
- call vol_to_realvol
- call [dword CARD_freq_convert]
- call [dword CARD_volume_convert]
- ret
- @@no_note_change:
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [byte edi+tfunk_chan.volume_portdest],dl
- call vol_to_realvol
- call [dword CARD_freq_convert]
- call [dword CARD_volume_convert]
- ret
- @@ReLOad_samples:
- call reload_sample_attr
- jmp @@no_note_change
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;0Com A: port up ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_port_up_log
- mov bl,[byte edi+tfunk_chan.note_com_val]
- and ebx,1111b
- movzx eax,[byte ebx+com_ifreq_inc]
- sub [dword edi+tfunk_chan.ifreq],eax
- cmp [dword edi+tfunk_chan.ifreq],300
- ja @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.ifreq],300
- @@done:
- mov ebx,[dword edi+tfunk_chan.ifreq]
- call ifreq_to_rfreq
- mov [dword edi+tfunk_chan.rfreq],eax
- call [dword CARD_freq_convert]
- ret
- endp
-
- proc com_port_up_lin
- mov bl,[byte edi+tfunk_chan.note_com_val]
- and ebx,1111b
- lea ebx,[ebx*4]
- mov eax,[dword ebx+com_rfreq_inc]
- add [dword edi+tfunk_chan.rfreq],eax
- cmp [dword edi+tfunk_chan.rfreq],174deh
- jb @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.rfreq],174deh
- @@done:
- call [dword CARD_freq_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;1Com B: port down ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_port_dn_log
- mov bl,[byte edi+tfunk_chan.note_com_val]
- and ebx,1111b
- movzx eax,[byte ebx+com_ifreq_inc]
- add [dword edi+tfunk_chan.ifreq],eax
- cmp [dword edi+tfunk_chan.ifreq],20000
- jb @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.ifreq],20000
- @@done:
- mov ebx,[dword edi+tfunk_chan.ifreq]
- call ifreq_to_rfreq
- mov [dword edi+tfunk_chan.rfreq],eax
- call [dword CARD_freq_convert]
- ret
- endp
-
- proc com_port_dn_lin
- mov bl,[byte edi+tfunk_chan.note_com_val]
- and ebx,1111b
- lea ebx,[ebx*4]
- mov eax,[dword ebx+com_rfreq_inc]
- sub [dword edi+tfunk_chan.rfreq],eax
- cmp [dword edi+tfunk_chan.rfreq],1431
- ja @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.rfreq],1431
- @@done:
- call [dword CARD_freq_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;2Com C: port to note ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_porta_log
- mov eax,[dword edi+tfunk_chan.ifreq_portdest]
- cmp [dword edi+tfunk_chan.ifreq],eax
- jne @@not_same
- mov [byte edi+tfunk_chan.note_command],0fh
- ret
- @@not_same:
- ja @@do_portup
- call com_port_dn_log
- mov eax,[dword edi+tfunk_chan.ifreq_portdest]
- cmp [dword edi+tfunk_chan.ifreq],eax
- jb @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.ifreq],eax
- jmp @@done
- @@do_portup:
- call com_port_up_log
- mov eax,[dword edi+tfunk_chan.ifreq_portdest]
- cmp [dword edi+tfunk_chan.ifreq],eax
- ja @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.ifreq],eax
- @@done:
- mov ebx,[dword edi+tfunk_chan.ifreq]
- call ifreq_to_rfreq
- mov [dword edi+tfunk_chan.rfreq],eax
- call [dword CARD_freq_convert]
- ret
- endp
-
- proc com_porta_lin
- mov eax,[dword edi+tfunk_chan.rfreq_portdest]
- cmp [dword edi+tfunk_chan.rfreq],eax
- jne @@not_same
- mov [byte edi+tfunk_chan.note_command],0fh
- ret
- @@not_same:
- jb @@do_portup
- call com_port_dn_lin
- mov eax,[dword edi+tfunk_chan.rfreq_portdest]
- cmp [dword edi+tfunk_chan.rfreq],eax
- ja @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.rfreq],eax
- jmp @@done
- @@do_portup:
- call com_port_up_lin
- mov eax,[dword edi+tfunk_chan.rfreq_portdest]
- cmp [dword edi+tfunk_chan.rfreq],eax
- jb @@done
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [dword edi+tfunk_chan.rfreq],eax
- @@done:
- call [dword CARD_freq_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc note_system_rapid_p1
- mov eax,[dword edi+tfunk_chan.note_command]
- cmp al,02h
- jbe @@do_rp1
- ret
- @@do_rp1:
- shr ah,4
- cmp [byte edi+tfunk_chan.note_comspd_count],ah
- jae @@speed_match
- inc [byte edi+tfunk_chan.note_comspd_count]
- ret
- @@speed_match:
- mov [byte edi+tfunk_chan.note_comspd_count],0
- cmp [byte edi+tfunk_chan.port_type],1
- je @@line_porta
- or al,al
- je @@command_a_i
- cmp al,01h
- je @@command_b_i
- cmp al,02h
- je @@command_c_i
- ret
- @@line_porta:
- or al,al
- je @@command_a_r
- cmp al,01h
- je @@command_b_r
- cmp al,02h
- je @@command_c_r
- ret
- @@command_a_i:
- call com_port_up_log
- ret
- @@command_a_r:
- call com_port_up_lin
- ret
- @@command_b_i:
- call com_port_dn_log
- ret
- @@command_b_r:
- call com_port_dn_lin
- ret
- @@command_c_i:
- call com_porta_log
- ret
- @@command_c_r:
- call com_porta_lin
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;3Com D: vibrato ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \speed/ \amplitude/ ;
- ; ;
- ;vib_waveform = 0 : sine ;
- ; 1 : triangle ;
- ; 2 : square ;
- ; 3 : sawtooth ;
- ; 4 : random ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vibrato
- mov ah,[byte edi+tfunk_chan.note_com_val]
- mov cl,ah
- and ah,00001111b
- shr cl,4
- proc com_vibrato_minor
- movzx ebx,[byte edi+tfunk_chan.vib_ptr]
- mov al,[byte edi+tfunk_chan.vib_waveform]
- call com_vib_func
- mov [byte edi+tfunk_chan.vib_ptr],bl
- movsx eax,al
- shl eax,1
- mov [dword edi+tfunk_chan.ifreq_vibrato],eax
- mov ebx,[dword edi+tfunk_chan.ifreq]
- call ifreq_to_rfreq_vib
- mov [dword edi+tfunk_chan.rfreq],eax
- call [dword CARD_freq_convert]
- ret
- endp
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;4Com E: vibrato Fanin ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \speed/ \fanin value/ ;
- ; ;
- ;vib_waveform = 0 : sine ;
- ; 1 : triangle ;
- ; 2 : square ;
- ; 3 : sawtooth ;
- ; 4 : random ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vib_fanin
- mov ah,[byte edi+tfunk_chan.note_com_val]
- mov cl,ah
- and ah,00001111b
- and cl,11110000b
- shr cl,2
- cmp [byte edi+tfunk_chan.note_beat_count],0fh
- jae @@do_vibrato
- cmp [byte edi+tfunk_chan.note_comspd_count],cl
- jae @@inc_fan
- inc [byte edi+tfunk_chan.note_comspd_count]
- jmp @@do_vibrato
- @@inc_fan:
- mov [byte edi+tfunk_chan.note_comspd_count],0
- inc [byte edi+tfunk_chan.note_beat_count]
- @@do_vibrato:
- mov cl,[byte edi+tfunk_chan.note_beat_count]
- call com_vibrato_minor
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;5Com F: vibrato Fanout ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \speed/ \fanin value/ ;
- ; ;
- ;vib_waveform = 0 : sine ;
- ; 1 : triangle ;
- ; 2 : square ;
- ; 3 : sawtooth ;
- ; 4 : random ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vib_fanout
- mov ah,[byte edi+tfunk_chan.note_com_val]
- mov cl,ah
- and ah,00001111b
- and cl,11110000b
- shr cl,2
- cmp [byte edi+tfunk_chan.note_beat_count],0
- je @@do_vibrato
- cmp [byte edi+tfunk_chan.note_comspd_count],cl
- jae @@dec_fan
- inc [byte edi+tfunk_chan.note_comspd_count]
- jmp @@do_vibrato
- @@dec_fan:
- mov [byte edi+tfunk_chan.note_comspd_count],0
- dec [byte edi+tfunk_chan.note_beat_count]
- @@do_vibrato:
- mov cl,[byte edi+tfunk_chan.note_beat_count]
- call com_vibrato_minor
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;6Com G: volume sld up ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vol_up
- mov bl,[byte edi+tfunk_chan.volume_com_val]
- and ebx,1111b
- mov al,[byte ebx+com_volume_inc]
- mov ah,[byte edi+tfunk_chan.volume]
- add ah,al
- jnc @@adjust
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],255
- jmp @@done
- @@adjust:
- mov [byte edi+tfunk_chan.volume],ah
- @@done:
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;7Com H: volume slide down ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vol_dn
- mov bl,[byte edi+tfunk_chan.volume_com_val]
- and ebx,1111b
- mov al,[byte ebx+com_volume_inc]
- mov ah,[byte edi+tfunk_chan.volume]
- sub ah,al
- jnc @@adjust
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],0
- jmp @@done
- @@adjust:
- mov [byte edi+tfunk_chan.volume],ah
- @@done:
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;8Com I: volume porta (Rapid ctrl) ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vol_porta
- mov al,[byte edi+tfunk_chan.volume_portdest]
- cmp [byte edi+tfunk_chan.volume],al
- jne @@not_same
- mov [byte edi+tfunk_chan.volume_command],0fh
- jmp @@done
- @@not_same:
- jb @@do_portup
- call com_vol_dn
- mov al,[byte edi+tfunk_chan.volume_portdest]
- cmp [byte edi+tfunk_chan.volume],al
- ja @@done
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],al
- jmp @@done
- @@do_portup:
- call com_vol_up
- mov al,[byte edi+tfunk_chan.volume_portdest]
- cmp [byte edi+tfunk_chan.volume],al
- jb @@done
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],al
- @@done:
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc volume_system_rapid_p1
- mov eax,[dword edi+tfunk_chan.volume_command]
- cmp al,06h
- jae @@do_rp1
- ret
- @@do_rp1:
- cmp al,08h
- jbe @@do_rp2
- ret
- @@do_rp2:
- shr ah,4
- cmp [byte edi+tfunk_chan.volume_comspd_count],ah
- jae @@speed_match
- inc [byte edi+tfunk_chan.volume_comspd_count]
- ret
- @@speed_match:
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- cmp al,06h
- je @@command_g
- cmp al,07h
- je @@command_h
- cmp al,08h
- je @@command_i
- ret
- @@command_g:
- call com_vol_up
- ret
- @@command_h:
- call com_vol_dn
- ret
- @@command_i:
- call com_vol_porta
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;9Com J: Volume Reverb ;
- ; ;
- ; A simulated echo effect ;
- ; ;
- ; com_val : 0000 0000 ;
- ; ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_reverb
- mov cl,[byte edi+tfunk_chan.volume_com_val]
- mov ch,cl
- mov dl,cl
- and ch,00001111b
- and cl,11110000b
- shr cl,2
- cmp [byte edi+tfunk_chan.volume_comspd_count],cl
- jae @@echo
- inc [byte edi+tfunk_chan.volume_comspd_count]
- @@do_slide:
- cmp [byte edi+tfunk_chan.volume],0
- je @@done
- movzx ecx,ch
- mov al,[byte ecx+com_volume_inc]
- mov ah,[byte edi+tfunk_chan.volume]
- sub ah,al
- jnc @@adjust
- mov [byte edi+tfunk_chan.volume],0
- jmp @@done
- @@adjust:
- mov [byte edi+tfunk_chan.volume],ah
- @@done:
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- @@echo:
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- neg dl
- shr dl,4
- sub [byte edi+tfunk_chan.volume_beat_count],dl
- jc @@end
- mov al,[byte edi+tfunk_chan.volume_beat_count]
- mov [byte edi+tfunk_chan.volume],al
- jmp @@done
- @@end:
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],0
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;ACom K: tremola ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_tremola
- mov ah,[byte edi+tfunk_chan.volume_com_val]
- mov cl,ah
- and ah,00001111b
- shr cl,4
- movzx ebx,[byte edi+tfunk_chan.vol_vib_ptr]
- mov al,[byte edi+tfunk_chan.vol_vib_waveform]
- call com_vib_func
- mov [byte edi+tfunk_chan.vol_vib_ptr],bl
- mov [byte edi+tfunk_chan.volume_vibrato],al
- call vol_to_realvol_vib
- call [dword CARD_volume_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;BCom L: arpeggio ;
- ; ;
- ; com_val : 0000 0000 ;
- ; \N1/ \N2/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_arpeggio
- mov al,[byte edi+tfunk_chan.note_com_val]
- mov bh,[byte edi+tfunk_chan.arp_speed]
- cmp [byte edi+tfunk_chan.note_comspd_count],bh
- jae @@speed_match
- inc [byte edi+tfunk_chan.note_comspd_count]
- ret
- @@speed_match:
- mov [byte edi+tfunk_chan.note_comspd_count],0
- mov bl,[byte edi+tfunk_chan.note]
- cmp [byte edi+tfunk_chan.note_beat_count],1 ; arp_type 1
- je @@arp1_t1
- cmp [byte edi+tfunk_chan.note_beat_count],2
- je @@arp1_t2
- jmp @@done
- @@arp1_t1:
- shr al,4
- jmp @@arp_it
- @@arp1_t2:
- and al,1111b
- @@arp_it:
- add bl,al
- cmp bl,59
- jbe @@done
- mov bl,[byte edi+tfunk_chan.note]
- @@done:
- @note_2_ifreq
- mov [dword edi+tfunk_chan.ifreq],ebx
- call ifreq_to_rfreq
- mov [dword edi+tfunk_chan.rfreq],eax
- call [dword CARD_freq_convert]
- cmp [byte edi+tfunk_chan.note_beat_count],2
- je @@clr_b
- inc [byte edi+tfunk_chan.note_beat_count]
- ret
- @@clr_b:
- mov [byte edi+tfunk_chan.note_beat_count],0
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;CCom M: sample offset ;
- ; ;
- ; This is a all present sample ;
- ; offset that is effective all the ;
- ; time for a given channel ;
- ; ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_sample_offset
- movzx eax,[byte edi+tfunk_chan.com_val]
- mov cl,[byte edi+tfunk_chan.sample_ofs_parm]
- shl eax,cl
- add [dword edi+tfunk_chan.CARD_sample_ptr],eax
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;DCom N: volume ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_volume
- mov al,[byte edi+tfunk_chan.volume_com_val]
- mov [byte edi+tfunk_chan.volume],al
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;ECom O0: misc control ;
- ; ;
- ;value control set ;
- ;------------------ ;
- ;0 vibrato sine ;
- ;1 vibrato triangle ;
- ;2 vibrato square ;
- ;3 vibrato sawtooth ;
- ;4 vibrato random ;
- ;5 tremola sine ;
- ;6 tremola triangle ;
- ;7 tremola square ;
- ;8 tremola sawtooth ;
- ;9 tremola random ;
- ;a halt note system ;
- ;b halt volume system ;
- ;c halt all systems ;
- ;d invert funkcrtl ;
- ;e algorithmic porting ;
- ;f linear porting ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_misccrtl
- mov al,[byte edi+tfunk_chan.com_val]
- and al,00001111b
- or al,al
- jz @@vib_sine
- cmp al,01h
- je @@vib_triangle
- cmp al,02h
- je @@vib_square
- cmp al,03h
- je @@vib_sawtooth
- cmp al,04h
- je @@vib_random
- cmp al,05h
- je @@trm_sine
- cmp al,06h
- je @@trm_triangle
- cmp al,07h
- je @@trm_square
- cmp al,08h
- je @@trm_sawtooth
- cmp al,09h
- je @@trm_random
- cmp al,0ah
- je @@halt_note_sys
- cmp al,0bh
- je @@halt_vol_sys
- cmp al,0ch
- je @@halt_all_sys
- cmp al,0dh
- je @@invert_funk
- cmp al,0eh
- je @@log_porta
- cmp al,0fh
- je @@lin_porta
- ret
- @@vib_sine:
- mov [byte edi+tfunk_chan.vib_waveform],0
- ret
- @@vib_triangle:
- mov [byte edi+tfunk_chan.vib_waveform],1
- ret
- @@vib_square:
- mov [byte edi+tfunk_chan.vib_waveform],2
- ret
- @@vib_sawtooth:
- mov [byte edi+tfunk_chan.vib_waveform],3
- ret
- @@vib_random:
- mov [byte edi+tfunk_chan.vib_waveform],4
- ret
- @@trm_sine:
- mov [byte edi+tfunk_chan.vol_vib_waveform],0
- ret
- @@trm_triangle:
- mov [byte edi+tfunk_chan.vol_vib_waveform],1
- ret
- @@trm_square:
- mov [byte edi+tfunk_chan.vol_vib_waveform],2
- ret
- @@trm_sawtooth:
- mov [byte edi+tfunk_chan.vol_vib_waveform],3
- ret
- @@trm_random:
- mov [byte edi+tfunk_chan.vol_vib_waveform],4
- ret
- @@halt_note_sys:
- mov [byte edi+tfunk_chan.note_command],0fh
- ret
- @@halt_vol_sys:
- mov [byte edi+tfunk_chan.volume_command],0fh
- ret
- @@halt_all_sys:
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [byte edi+tfunk_chan.volume_command],0fh
- ret
- @@invert_funk:
- xor [byte edi+tfunk_chan.funkctrl],1b
- mov [byte edi+tfunk_chan.start],0
- ret
- @@log_porta:
- mov [byte edi+tfunk_chan.port_type],0
- ret
- @@lin_porta:
- mov [byte edi+tfunk_chan.port_type],1
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O1: volume cut ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_volume_cut
- mov al,[byte edi+tfunk_chan.volume_com_val]
- and al,1111b
- cmp [byte edi+tfunk_chan.volume_comspd_count],al
- jae @@speed_match
- inc [byte edi+tfunk_chan.volume_comspd_count]
- ret
- @@speed_match:
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],0
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O2: real frequency adjust ;
- ; ;
- ; - this adjustment is independant ;
- ; and is post added ;
- ; - this is a real frequency ;
- ; adjustment ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_real_freqad
- mov al,[byte edi+tfunk_chan.com_val]
- and eax,1111b
- shl eax,3
- mov [dword edi+tfunk_chan.rfreq_adjust],eax
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O3: set arpeggio speed ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_arp_speed_set
- mov al,[byte edi+tfunk_chan.com_val]
- and al,1111b
- mov [byte edi+tfunk_chan.arp_speed],al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O4: fine port_up ;
- ; ;
- ; com_val : 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_fine_port_up
- cmp [byte edi+tfunk_chan.port_type],1
- je @@line_porta
- call com_port_up_log
- ret
- @@line_porta:
- call com_port_up_lin
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O5: fine port_dn ;
- ; ;
- ; com_val : 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_fine_port_dn
- cmp [byte edi+tfunk_chan.port_type],1
- je @@line_porta
- call com_port_dn_log
- ret
- @@line_porta:
- call com_port_dn_lin
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O6: fine vol sld up ;
- ; ;
- ; com_val : 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O7: fine vol sld dn ;
- ; ;
- ; com_val : 0000 ;
- ; \rate/ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O8: volume crest ;
- ; ;
- ; com_val : 0000 ;
- ; \speed/ (prehand);
- ; ;
- ; volume slides up then down, ;
- ; starting at current frequency ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vol_crest
- mov bl,[byte edi+tfunk_chan.volume_com_val]
- and ebx,1111b
- mov dl,[byte ebx+com_volume_inc]
- cmp [byte edi+tfunk_chan.volume_beat_count],1
- je @@wait_a_bit
- cmp [byte edi+tfunk_chan.volume_beat_count],2
- je @@slide_down
- add [byte edi+tfunk_chan.volume],dl
- jc @@second_phase
- @@done:
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- @@second_phase:
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- inc [byte edi+tfunk_chan.volume_beat_count]
- mov [byte edi+tfunk_chan.volume],0ffh
- jmp @@done
- @@wait_a_bit:
- inc bl
- neg bl
- and bl,1111b
- cmp [byte edi+tfunk_chan.volume_comspd_count],bl
- jae @@speed_match
- inc [byte edi+tfunk_chan.volume_comspd_count]
- ret
- @@speed_match:
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- inc [byte edi+tfunk_chan.volume_beat_count]
- ret
- @@slide_down:
- shr dl,2
- inc dl
- mov al,[byte edi+tfunk_chan.volume_portdest]
- sub [byte edi+tfunk_chan.volume],dl
- jc @@end
- cmp [byte edi+tfunk_chan.volume],al
- ja @@done
- @@end:
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],al
- jmp @@done
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com O9: volume trough ;
- ; ;
- ; com_val : 0000 ;
- ; \speed/ (prehand);
- ; ;
- ; volume slides down then up, ;
- ; starting at current frequency ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_vol_trough
- mov bl,[byte edi+tfunk_chan.volume_com_val]
- and ebx,1111b
- mov dl,[byte ebx+com_volume_inc]
- cmp [byte edi+tfunk_chan.volume_beat_count],1
- je @@wait_a_bit
- cmp [byte edi+tfunk_chan.volume_beat_count],2
- je @@slide_down
- shr dl,2
- inc dl
- sub [byte edi+tfunk_chan.volume],dl
- jc @@second_phase
- @@done:
- call vol_to_realvol
- call [dword CARD_volume_convert]
- ret
- @@second_phase:
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- inc [byte edi+tfunk_chan.volume_beat_count]
- mov [byte edi+tfunk_chan.volume],0
- jmp @@done
- @@wait_a_bit:
- inc bl
- neg bl
- and bl,1111b
- cmp [byte edi+tfunk_chan.volume_comspd_count],bl
- jae @@speed_match
- inc [byte edi+tfunk_chan.volume_comspd_count]
- ret
- @@speed_match:
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- inc [byte edi+tfunk_chan.volume_beat_count]
- ret
- @@slide_down:
- mov al,[byte edi+tfunk_chan.volume_portdest]
- add [byte edi+tfunk_chan.volume],dl
- jc @@end
- cmp [byte edi+tfunk_chan.volume],al
- jb @@done
- @@end:
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume],al
- jmp @@done
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com OA: master volume set ;
- ; ;
- ; master effects all volumes, good ;
- ; for fading songs in and out ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_master_set
- mov al,[byte edi+tfunk_chan.com_val]
- and al,1111b
- mov [byte funk_info.master_volume],al
- push edi
- lea edi,[funk_chan1]
- mov cl,8
- @@sync_volume:
- push ecx
- call [dword CARD_volume_convert]
- add edi,size tfunk_chan
- pop ecx
- dec cl
- jnz @@sync_volume
- pop edi
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com OB: expand loop ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_expand_loop
- mov al,[byte edi+tfunk_chan.com_val]
- and eax,1111b
- inc al
- mov cl,[byte edi+tfunk_chan.sample_ofs_parm]
- shl eax,cl
- sub [dword edi+tfunk_chan.start],eax
- or [byte edi+tfunk_chan.funkctrl],10000000b
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com OC: colapse loop ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_colapse_loop
- mov al,[byte edi+tfunk_chan.com_val]
- and eax,1111b
- inc al
- mov cl,[byte edi+tfunk_chan.sample_ofs_parm]
- shl eax,cl
- add [dword edi+tfunk_chan.start],eax
- or [byte edi+tfunk_chan.funkctrl],10000000b
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com OD: note retrig ;
- ; ;
- ; com_val : ???? 0000 ;
- ; \speed/ (prehand);
- ; ;
- ; command only handled on full ;
- ; or sample only slots ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_note_retrig
- mov al,[byte edi+tfunk_chan.com_val]
- and al,00001111b
- cmp [byte edi+tfunk_chan.retrig_spd_count],al
- jae @@speed_match
- inc [byte edi+tfunk_chan.retrig_spd_count]
- ret
- @@speed_match:
- mov [byte edi+tfunk_chan.retrig_spd_count],0
-
- mov al,[byte edi+tfunk_chan.retrig_limit]
- cmp [byte edi+tfunk_chan.retrig_count],al
- jae @@done
- inc [byte edi+tfunk_chan.retrig_count]
- mov al,[byte edi+tfunk_chan.sample]
- call do_retrig_sample
- ret
- @@done:
- mov [byte edi+tfunk_chan.command],0fh
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com OE: set channel balance ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_balance
- mov al,[byte edi+tfunk_chan.com_val]
- shl al,4
- mov [byte edi+tfunk_chan.balance],al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; Com OF: tempo ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_tempo
- mov al,[byte edi+tfunk_chan.com_val]
- and al,1111b
- mov [byte funk_info.tempo],al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Command control for null slots only ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_null_ctrl
- mov eax,[dword edi+tfunk_chan.command]
- and eax,1111111100001111b
- cmp al,0fh
- je @@command_idle
- or al,al ; com a
- je @@ns_basic
- cmp al,01h ; com b
- je @@ns_basic
- cmp al,02h ; com c
- je @@ns_basic
- cmp al,03h ; com d
- je @@ns_basic
- cmp al,04h ; com e
- je @@command_e
- cmp al,05h ; com f
- je @@command_f
- cmp al,06h ; com g
- je @@vs_basic
- cmp al,07h ; com h
- je @@vs_basic
- cmp al,08h ; com i
- je @@vs_basic
- cmp al,09h ; com j
- je @@command_j
- cmp al,0ah ; com k
- je @@vs_basic
- cmp al,0bh ; com l
- je @@command_l
- cmp al,0dh ; com n
- je @@command_n
- mov ebx,eax
- and bh,11110000b
- cmp ebx,0000eh ; com o0
- je @@command_o0
- cmp ebx,0100eh ; com o1
- je @@vs_basic
- cmp ebx,0200eh ; com o2
- je @@command_o2
- cmp ebx,0300eh ; com o3
- je @@command_o3
- cmp ebx,0400eh ; com o4
- je @@command_o4
- cmp ebx,0500eh ; com o5
- je @@command_o5
- cmp ebx,0600eh ; com o6
- je @@command_o6
- cmp ebx,0700eh ; com o7
- je @@command_o7
- cmp ebx,0800eh ; com o8
- je @@command_o8o9
- cmp ebx,0900eh ; com o9
- je @@command_o8o9
- cmp ebx,0a00eh ; com oa
- je @@command_oa
- cmp ebx,0b00eh ; com ob
- je @@command_ob
- cmp ebx,0c00eh ; com oc
- je @@command_oc
- cmp ebx,0e00eh ; com oe
- je @@command_oe
- cmp ebx,0f00eh ; com of
- je @@command_of
- ret
- @@ns_basic:
- mov [word edi+tfunk_chan.note_command],ax
- mov [byte edi+tfunk_chan.note_comspd_count],0
- ret
- @@vs_basic:
- mov [word edi+tfunk_chan.volume_command],ax
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- ret
- @@command_e:
- mov [byte edi+tfunk_chan.note_beat_count],0
- jmp @@set_vib_fan
- @@command_f:
- mov [byte edi+tfunk_chan.note_beat_count],0fh
- @@set_vib_fan:
- cmp [byte edi+tfunk_chan.note_command],03h ; if vibrato command
- jne @@dont_set_vib
- mov bl,[byte edi+tfunk_chan.note_com_val]
- shr bl,4
- mov [byte edi+tfunk_chan.note_beat_count],bl
- @@dont_set_vib:
- mov [word edi+tfunk_chan.note_command],ax
- mov [byte edi+tfunk_chan.note_comspd_count],0
- ret
- @@command_j:
- mov [word edi+tfunk_chan.volume_command],ax
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- mov al,[byte edi+tfunk_chan.volume]
- mov [byte edi+tfunk_chan.volume_beat_count],al
- ret
- @@command_l:
- mov [word edi+tfunk_chan.note_command],ax
- mov [byte edi+tfunk_chan.note_comspd_count],0
- mov [byte edi+tfunk_chan.note_beat_count],1
- ret
- @@command_n:
- mov [word edi+tfunk_chan.volume_command],ax
- call com_volume
- ret
- @@command_o0:
- call com_misccrtl
- ret
- @@command_o2:
- call com_real_freqad
- call [dword CARD_volume_convert]
- ret
- @@command_o3:
- call com_arp_speed_set
- ret
- @@command_o4:
- mov [word edi+tfunk_chan.note_command],ax
- call com_fine_port_up
- ret
- @@command_o5:
- mov [word edi+tfunk_chan.note_command],ax
- call com_fine_port_dn
- ret
- @@command_o6:
- mov [word edi+tfunk_chan.volume_command],ax
- call com_vol_up
- ret
- @@command_o7:
- mov [word edi+tfunk_chan.volume_command],ax
- call com_vol_dn
- ret
- @@command_o8o9:
- mov [word edi+tfunk_chan.volume_command],ax
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- mov [byte edi+tfunk_chan.volume_beat_count],0
- mov al,[byte edi+tfunk_chan.volume]
- mov [byte edi+tfunk_chan.volume_portdest],al
- ret
- @@command_oa:
- call com_master_set
- ret
- @@command_ob:
- call com_expand_loop
- ret
- @@command_oc:
- call com_colapse_loop
- ret
- @@command_oe:
- call com_balance
- ret
- @@command_of:
- call com_tempo
- ret
- @@command_idle:
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Command control for full slots ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_full_ctrl
- mov eax,[dword edi+tfunk_chan.command]
- and eax,1111111100001111b
- cmp al,0fh
- je @@command_idle
- or al,al ; com a
- je @@ns_basic
- cmp al,01h ; com b
- je @@ns_basic
- cmp al,02h ; com c
- je @@command_c
- cmp al,03h ; com d
- je @@ns_basic
- cmp al,04h ; com e
- je @@command_e
- cmp al,05h ; com f
- je @@command_f
- cmp al,06h ; com g
- je @@vs_basic
- cmp al,07h ; com h
- je @@vs_basic
- cmp al,08h ; com i
- je @@command_i
- cmp al,09h ; com j
- je @@command_j
- cmp al,0ah ; com k
- je @@vs_basic
- cmp al,0bh ; com l
- je @@command_l
- cmp al,0ch ; com m
- je @@command_m
- cmp al,0dh ; com n
- je @@command_n
- mov ebx,eax
- and bh,11110000b
- cmp ebx,0000eh ; com o0
- je @@command_o0
- cmp ebx,0100eh ; com o1
- je @@vs_basic
- cmp ebx,0200eh ; com o2
- je @@command_o2
- cmp ebx,0300eh ; com o3
- je @@command_o3
- cmp ebx,0400eh ; com o4
- je @@command_o4
- cmp ebx,0500eh ; com o5
- je @@command_o5
- cmp ebx,0600eh ; com o6
- je @@command_o6
- cmp ebx,0700eh ; com o7
- je @@command_o7
- cmp ebx,0800eh ; com o8
- je @@command_o8o9
- cmp ebx,0900eh ; com o9
- je @@command_o8o9
- cmp ebx,0a00eh ; com oa
- je @@command_oa
- cmp ebx,0b00eh ; com ob
- je @@command_ob
- cmp ebx,0c00eh ; com oc
- je @@command_oc
- cmp ebx,0d00eh ; com od
- je @@command_od
- cmp ebx,0e00eh ; com oe
- je @@command_oe
- cmp ebx,0f00eh ; com of
- je @@command_of
- ret
- @@ns_basic:
- mov [word edi+tfunk_chan.note_command],ax
- mov [byte edi+tfunk_chan.note_comspd_count],0
- call normal_decode_note
- ret
- @@vs_basic:
- mov [word edi+tfunk_chan.volume_command],ax
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- call normal_decode_volume
- ret
- @@command_c:
- mov [word edi+tfunk_chan.note_command],ax
- mov [byte edi+tfunk_chan.note_comspd_count],0
- call comc_decode
- ret
- @@command_e:
- mov [byte edi+tfunk_chan.note_beat_count],0
- jmp @@set_vib_fan
- @@command_f:
- mov [byte edi+tfunk_chan.note_beat_count],0fh
- @@set_vib_fan:
- cmp [byte edi+tfunk_chan.note_command],03h ; if vibrato command
- jne @@dont_set_vib
- mov bl,[byte edi+tfunk_chan.note_com_val]
- shr bl,4
- mov [byte edi+tfunk_chan.note_beat_count],bl
- @@dont_set_vib:
- mov [word edi+tfunk_chan.note_command],ax
- mov [byte edi+tfunk_chan.note_comspd_count],0
- call normal_decode_note
- ret
- @@command_i:
- mov [word edi+tfunk_chan.volume_command],ax
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- call comi_decode
- ret
- @@command_j:
- mov [word edi+tfunk_chan.volume_command],ax
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- call normal_decode_volume
- mov al,[byte edi+tfunk_chan.volume]
- mov [byte edi+tfunk_chan.volume_beat_count],al
- ret
- @@command_l:
- mov [word edi+tfunk_chan.note_command],ax
- mov [byte edi+tfunk_chan.note_comspd_count],0
- mov [byte edi+tfunk_chan.note_beat_count],1
- call normal_decode_note
- ret
- @@command_m:
- call normal_decode_system
- call com_sample_offset
- ret
- @@command_n:
- mov [word edi+tfunk_chan.volume_command],ax
- call normal_decode_volume
- call com_volume
- ret
- @@command_o0:
- call normal_decode_system
- call com_misccrtl
- ret
- @@command_o2:
- call com_real_freqad
- call normal_decode_system
- ret
- @@command_o3:
- call normal_decode_system
- call com_arp_speed_set
- ret
- @@command_o4:
- mov [word edi+tfunk_chan.note_command],ax
- call normal_decode_note
- call com_fine_port_up
- ret
- @@command_o5:
- mov [word edi+tfunk_chan.note_command],ax
- call normal_decode_note
- call com_fine_port_dn
- ret
- @@command_o6:
- mov [word edi+tfunk_chan.volume_command],ax
- call normal_decode_volume
- call com_vol_up
- ret
- @@command_o7:
- mov [word edi+tfunk_chan.volume_command],ax
- call normal_decode_volume
- call com_vol_dn
- ret
- @@command_o8o9:
- mov [word edi+tfunk_chan.volume_command],ax
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- mov [byte edi+tfunk_chan.volume_beat_count],0
- call normal_decode_volume
- mov al,[byte edi+tfunk_chan.volume]
- mov [byte edi+tfunk_chan.volume_portdest],al
- ret
- @@command_oa:
- call com_master_set
- call normal_decode_system
- ret
- @@command_ob:
- call normal_decode_system
- call com_expand_loop
- ret
- @@command_oc:
- call normal_decode_system
- call com_colapse_loop
- ret
- @@command_od:
- mov [byte edi+tfunk_chan.retrig_count],1
- mov [byte edi+tfunk_chan.retrig_spd_count],0
- call normal_decode_system
- ret
- @@command_oe:
- call normal_decode_system
- call com_balance
- ret
- @@command_of:
- call normal_decode_system
- call com_tempo
- ret
- @@command_idle:
- call normal_decode_system
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Command control for rapid "on the fly" ;
- ; Rapid commands that have a speed parameter ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc com_rapid_ctrl
- lea edi,[funk_chan1]
- mov cl,8
- @@play_slot:
- push ecx
-
- call note_system_rapid_p1
- call volume_system_rapid_p1
-
- mov eax,[dword edi+tfunk_chan.note_command]
- cmp al,03h ; command d
- je @@command_d
- cmp al,04h ; command e
- je @@command_e
- cmp al,05h ; command f
- je @@command_f
- cmp al,0bh ; command l
- je @@command_l
- jmp @@do_vol_com
- @@command_d:
- call com_vibrato
- jmp @@do_vol_com
- @@command_e:
- call com_vib_fanin
- jmp @@do_vol_com
- @@command_f:
- call com_vib_fanout
- jmp @@do_vol_com
- @@command_l:
- call com_arpeggio
- @@do_vol_com:
- mov eax,[dword edi+tfunk_chan.volume_command]
- cmp al,09h ; command j
- je @@command_j
- cmp al,0Ah ; command k
- je @@command_k
- and eax,1111000000001111b
- cmp eax,0100eh ; command o1
- je @@command_o1
- cmp eax,0800eh ; command o8
- je @@command_o8
- cmp eax,0900eh ; command o9
- je @@command_o9
- jmp @@system_final
- @@command_j:
- call com_reverb
- jmp @@system_final
- @@command_k:
- call com_tremola
- jmp @@system_final
- @@command_o1:
- call com_volume_cut
- jmp @@system_final
- @@command_o8:
- call com_vol_crest
- jmp @@system_final
- @@command_o9:
- call com_vol_trough
- @@system_final:
- mov eax,[dword edi+tfunk_chan.command]
- and eax,1111000000001111b
- cmp eax,0d00eh ; command od
- jne @@end_command
- call com_note_retrig
- @@end_command:
- pop ecx
- add edi,size tfunk_chan
- dec cl
- jnz @@play_slot
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; ESI = current pattern ;
- ; ;
- ; format: ;
- ; ;
- ; 00000000 11111111 22222222 ;
- ; \ /\ /\ / \ / ;
- ; note sample com command value ;
- ; ;
- ; - if note: = 3D, then reload sample attrs ;
- ; = 3F, then it's a null slot ;
- ; = 3E, then sample only slot ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc trekk_slot
- movzx eax,[byte funk_info.pattern_ofs] ;24 * al
- mov ebx,eax
- shl eax,4
- shl ebx,3
- add eax,ebx
- add esi,eax
-
- lea edi,[funk_chan1]
- mov cl,8
- @@play_slot:
- push ecx esi
- mov ax,[word esi+1] ;extract command and value
- and al,00001111b
- mov [word edi+tfunk_chan.command],ax
-
- mov al,[byte esi]
- shr al,2
- cmp al,03Fh ;IF FULL SLOT or SAMPLE
- jne @@full_cont ;ONLY SLOT
- call com_null_ctrl
- jmp @@next_channel
- @@full_cont:
- call com_full_ctrl
- @@next_channel:
- pop esi ecx
- add edi,size tfunk_chan
- add esi,3
- dec cl
- jnz @@play_slot
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; The actual tracker thingy :) ....0.02 second tick (or roughly) ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc funk_tracker
- cmp [byte funk_info.trek_status],STOP
- je @@dont_play
- call com_rapid_ctrl
- mov al,[byte funk_info.tempo]
- cmp [byte funk_info.tempo_count],al
- jb @@tempo_miss
- mov [byte funk_info.tempo_count],0
- movzx ebx,[byte funk_info.sequence_ofs]
- movzx esi,[byte ebx+funk_hr.order_list]
- mov eax,esi ; bx * 600h
- shl eax,10
- shl esi,9
- add esi,eax
- add esi,[dword funk_pd_ptr]
- call trekk_slot
- mov al,[byte funk_info.pattern_ofs]
- movzx ebx,[byte funk_info.sequence_ofs]
- movzx ebx,[byte ebx+funk_hr.order_list]
- mov al,[byte ebx+funk_hr.break_list]
- cmp [byte funk_info.pattern_ofs],al ;if done last pattern then...
- je @@change_pattern ;jump if no pattern cross
- inc [byte funk_info.pattern_ofs] ;add the trek slot ofs
- ret
- @@change_pattern:
- mov cl,[byte funk_info.no_of_sequences]
- cmp [byte funk_info.sequence_ofs],cl
- jb @@dont_loop_seq_ofs
- cmp [byte funk_hr.loop_order],0FFh
- jne @@set_loop_rippp
- mov [byte funk_info.trek_status],STOP
- @@set_loop_rippp:
- mov dl,[byte funk_hr.loop_order]
- dec dl
- mov [byte funk_info.sequence_ofs],dl
- @@dont_loop_seq_ofs:
- inc [byte funk_info.sequence_ofs]
- mov [byte funk_info.pattern_ofs],0
- ret
- @@tempo_miss:
- inc [byte funk_info.tempo_count]
- @@dont_play:
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc stop_all_voices
- cli
- lea edi,[funk_chan1]
- xor cl,cl
- @@play_slot:
- push ecx
- mov [byte edi+tfunk_chan.funkctrl],0
- mov [byte edi+tfunk_chan.volume],0
- mov [byte edi+tfunk_chan.rvolume],0
- call [dword CARD_volume_convert]
- pop ecx
- add edi,size tfunk_chan
- inc cl
- cmp cl,8
- jb @@play_slot
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; DMA routines (From DOS32) ;
- ; INPUT: AL Mode Register ( bits 0..1 ignored ) ;
- ; AH channel 0..7 ;
- ; EBX Physical Base Address ;
- ; ECX Bytes to transfer ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc DMA_Setup
- xor edx,edx
- and ah,7
- mov [@@DMA_channel],ah
- and al,NOT 3
- mov [@@mode],al
- movzx edi,[byte @@DMA_channel]
- mov eax,edi
- shr edi,2
- and al,0011b
- or al,0100b
- mov dl,[edi+@@DMA_SNGL]
- out dx,al
- call @@pause
- and al,03h
- or al,[@@Mode]
- mov dl,[edi+@@DMA_MODE]
- out dx,al
- call @@pause
- mov dl,[edi+@@DMA_CLRFF]
- out dx,al
- call @@pause
- movzx edi,[@@DMA_channel]
- mov eax,ecx
- mov ecx,edi
- shr ecx,2
- shr eax,cl
- mov dl,[edi+@@DMA_CNT]
- out dx,al
- call @@pause
- shr eax,8
- out dx,al
- call @@pause
- shr ebx,cl
- mov al,BL
- mov dl,[edi+@@DMA_ADDR]
- out dx,al
- call @@pause
- mov al,BH
- out dx,al
- call @@pause
- shr ebx,15
- xor cl,1
- shr ebx,cl
- mov al,BL
- mov dl,[edi+@@DMA_PAGE]
- out dx,al
- call @@pause
- mov eax,edi
- shr edi,2
- and al,03h
- mov dl,[edi+@@DMA_SNGL]
- out dx,al
- call @@pause
- ret
- @@Mode db ?
- @@DMA_Channel db ?
- @@DMA_STAT db 008h,0D0h
- @@DMA_CMD db 008h,0D0h
- @@DMA_REQ db 009h,0D2h
- @@DMA_SNGL db 00Ah,0D4h
- @@DMA_MODE db 00Bh,0D6h
- @@DMA_CLRFF db 00Ch,0D8h
- @@DMA_MCLR db 00Dh,0DAh
- @@DMA_CLRM db 00Eh,0DCh
- @@DMA_WRTALL db 00Fh,0DEh
- @@DMA_PAGE db 087h,083h,081h,082h,08Fh,08Bh,089h,08Ah
- @@DMA_ADDR db 000h,002h,004h,006h,0C0h,0C4h,0C8h,0CCh
- @@DMA_CNT db 001h,003h,005h,007h,0C2h,0C6h,0CAh,0CEh
- proc @@pause
- jmp @@j
- @@j:
- ret
- endp
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; DAC INDEPENDANT CODE ;
- ; ;
- ; These routines are general DAC routines used by all DAC soundcards. ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- DAC_old_irq_ofs dd 0
- DAC_old_irq_sel dw 0
- DAC_mix_buffer_size dd ?
- DAC_sampling_rate dd ?
- DMA_length dd 4000h
-
- DAC_mb_offs = 0
- DAC_mb_right_offs = 1000h
- DAC_mb2_offs = 2000h
- DAC_mix_buffer dd DAC_mb_offs
- DAC_mix_buffer_right dd DAC_mb_right_offs
- DAC_mix_buffer2 dd DAC_mb2_offs
- DAC_PHYSICAL_PAGE dd DAC_mb2_offs
- DAC_shift_value db 0
- DAC_double_buf1 dd 0
- DAC_double_buf2 dd 0
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc DACi_freq_convert
- mov eax,[dword edi+tfunk_chan.rfreq]
- mov edx,eax
- shl eax,16
- shr edx,16
- div [dword DAC_sampling_rate]
- mov [dword edi+tfunk_chan.CARD_freq],eax
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc DACi_volume_convert
- xor eax,eax
- cmp [byte edi+tfunk_chan.channel_kill],STOP
- je @@transt
- mov al,[byte funk_info.master_volume]
- cmp al,0
- je @@transt
- xor ecx,ecx
- mov cl,[byte edi+tfunk_chan.rvolume]
- inc al
- mul ecx
- mov cl,[byte DAC_shift_value]
- shr eax,cl
- @@transt:
- mov [byte edi+tfunk_chan.CARD_volume],al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; unit channel DAC buffer Mixer ;
- ; ;
- ; ebx = channel ptr, edi = buffer ;
- ; ;
- ; 00 ;
- ; ||_____ 1=loop sample ;
- ; | ;
- ; |______ DAC sample play ;
- ; ;
- ; ===================================================================== ;
- ; ;
- ; This is the heart of DAC mixxing. Here we actually mix a given channel ;
- ; to the mixing buffer. This code does frequency transformations and volume;
- ; manipulation (it's what the DSP cards do interally). If a Card does this ;
- ; in hardware, then it is refered to as a "DSP" card rather than a "DAC" ;
- ; card. An example of a "DSP" card is the Gravis Ultrasound card. ;
- ; ;
- ; The frequency transformer belongs to Tom Verbeure...thanks tom! ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc DAC_channel_mixxer
- mov ch,[byte ebx+tfunk_chan.funkctrl]
- mov cl,[byte ebx+tfunk_chan.CARD_volume]
- mov edx,[dword ebx+tfunk_chan.CARD_freq]
- mov ebp,edx
- shl edx,16
- shr ebp,16
- mov esi,[dword ebx+tfunk_chan.CARD_sample_ptr]
- mov eax,[dword DAC_mix_buffer_size]
- @@mix_loop:
- push eax
- test ch,10b
- jnz @@run_sample
- xor al,al
- jmp @@trans_sample
- @@run_sample:
- mov al,[byte esi]
- @@trans_sample:
- imul cl
- add [word edi],ax
- add edi,2
- add [dword ebx+tfunk_chan.CARD_freq_attract],edx
- adc esi,ebp
- cmp esi,[dword ebx+tfunk_chan.length]
- jb @@comp_end
- test ch,01b
- jnz @@loop_back
- and ch,01b
- jmp @@comp_end
- @@loop_back:
- mov esi,[dword ebx+tfunk_chan.start]
- @@comp_end:
- pop eax
- dec eax
- jnz @@mix_loop
- mov [byte ebx+tfunk_chan.funkctrl],ch
- mov [dword ebx+tfunk_chan.CARD_sample_ptr],esi
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; SB DEPENDANT CODE ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- SB_INTR_8BITDMA = 1
- SB_INTR_16BITDMA = 2
- SB_INTR_MPU401 = 4
-
- SB_BASE dd ?
- SB_MIXER dd ?
- SB_RESET dd ?
- SB_READ_DATA dd ?
- SB_WRITE_DATA dd ?
- SB_DATA_AVAIL dd ?
- SB_DATA_AVAIL16 dd ?
-
- SB_trig dd ?
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB_write_dac
- push eax
- mov edx,[dword SB_WRITE_DATA]
- @@Wait_Ready:
- in al,dx
- and al,80h
- jnz @@Wait_Ready
- pop eax
- out dx,al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; al = addr ah = data SBPRO mixxer ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB_write_mixer
- mov edx,[dword SB_MIXER]
- push edx
- out dx,al
- pop edx
- inc dx
- mov al,ah
- out dx,al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; DMA trigs ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB_trig_compatable
- mov al,14h ;DMA_8_BIT_DAC
- call SB_write_dac
- mov eax,[dword DMA_length]
- dec eax
- call SB_write_dac
- mov al,ah
- call SB_write_dac
- ret
- endp
-
- proc SB_trig_advanced
- mov al,91h
- call SB_write_dac
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB_virtualmixxer
- cld
- push ds es
- pushad
- mov ax,[word cs:DATA32_sel]
- mov ds,ax
- mov es,ax
- mov edx,[dword SB_DATA_AVAIL]
- in al,dx
- call [dword SB_trig]
- mov esi,[dword DAC_mix_buffer]
- mov edi,[dword DAC_mix_buffer2]
- add edi,[DAC_double_buf1]
- mov eax,[DAC_double_buf1]
- xchg eax,[DAC_double_buf2]
- mov [DAC_double_buf1],eax
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- @@trans8:
- mov eax,[esi]
- mov al,ah
- mov [edi],al
- mov eax,[esi+2]
- mov al,ah
- mov [edi+1],al
- add esi,4
- add edi,2
- dec ecx
- jnz @@trans8
- call funk_tracker
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- mov edi,[dword DAC_mix_buffer]
- mov eax,80008000h
- rep stosd
- lea ebx,[funk_chan1]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan2]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan3]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan4]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan5]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan6]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan7]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan8]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- mov al,20h
- out 20h,al
- popad
- pop es ds
- iretd
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SBPRO_virtualmixxer
- cld
- push ds es
- pushad
- mov ax,[word cs:DATA32_sel]
- mov ds,ax
- mov es,ax
- mov edx,[dword SB_DATA_AVAIL]
- in al,dx
- call [dword SB_trig]
- mov esi,[dword DAC_mix_buffer]
- mov edi,[dword DAC_mix_buffer2]
- add edi,[DAC_double_buf1]
- mov eax,[DAC_double_buf1]
- xchg eax,[DAC_double_buf2]
- mov [DAC_double_buf1],eax
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- @@trans8:
- mov eax,[esi+DAC_mb_right_offs]
- mov al,ah
- mov ah,[byte esi+1+DAC_mb_offs]
- mov [edi],ax
- mov eax,[esi+2+DAC_mb_right_offs]
- mov al,ah
- mov ah,[byte esi+3+DAC_mb_offs]
- mov [edi+2],ax
- add esi,4
- add edi,4
- dec ecx
- jnz @@trans8
- call funk_tracker
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- mov edi,[dword DAC_mix_buffer]
- mov eax,80008000h
- rep stosd
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- mov edi,[dword DAC_mix_buffer_right]
- rep stosd
- lea ebx,[funk_chan1]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan2]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan3]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan4]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan5]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan6]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan7]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan8]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- mov al,20h
- out 20h,al
- popad
- pop es ds
- iretd
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB16_virtualmixxer
- cld
- push ds es
- pushad
- mov ax,[word cs:DATA32_sel]
- mov ds,ax
- mov es,ax
- mov edx,[SB_MIXER]
- mov al,82h
- out dx,al
- inc edx
- in al,dx
- test al,02h
- jz @@chainpreviousISR
- mov edx,[dword SB_DATA_AVAIL16]
- in al,dx
- mov esi,[dword DAC_mix_buffer]
- mov edx,[dword DAC_mix_buffer_right]
- mov edi,[dword DAC_mix_buffer2]
- add edi,[DAC_double_buf1]
- mov eax,[DAC_double_buf1]
- xchg eax,[DAC_double_buf2]
- mov [DAC_double_buf1],eax
- mov ecx,[dword DAC_mix_buffer_size]
- xor ebx,ebx
- @@trans16:
- mov eax,[edx+ebx]
- shl eax,16
- mov ax,[word esi+ebx]
- mov [edi+ebx*2],eax
- add ebx,2
- dec ecx
- jnz @@trans16
- call funk_tracker
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- mov edi,[dword DAC_mix_buffer]
- xor eax,eax
- rep stosd
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- mov edi,[dword DAC_mix_buffer_right]
- rep stosd
- lea ebx,[funk_chan1]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan2]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan3]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan4]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan5]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan6]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan7]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan8]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- jmp @@ExitISR
- @@chainpreviousISR:
- @@ExitISR:
- mov al,20h
- out 20h,al
- popad
- pop es ds
- iretd
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; BLASTER=A220 I7 D1 T4 (old format) ;
- ; \ ;
- ; ------ T1 = SB 1.0 ;
- ; T2 = SB 1.5 ;
- ; T3 = SB 2.0 ;
- ; T4 = SBPRO ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB_env
- push es
- mov es,[word Zero_SEL]
- mov ah,62h ; Get the PSP segment
- int 21h
- movzx edi,bx
- shl edi,4
- movzx edi,[word es:edi+2Ch] ; Get the Environment segment value
- shl edi,4
- mov ecx,10000h
- @@SrchEnvrLoop:
- lea esi,[@@blaster_string]
- mov ecx,8
- repe cmpsb
- jne @@No_SBstring
- dec edi
- call @@skip
- cmp [byte es:edi],"A"
- jne @@No_BLASTER
- inc edi
- mov bh,[byte es:edi]
- sub bh,"0"
- inc edi
- mov bl,[byte es:edi]
- sub bl,"0"
- shl bl,4
- inc edi
- mov al,[byte es:edi]
- sub al,"0"
- or bl,al
- mov [word init_settings.PORT_no],bx
- call @@skip
- cmp [byte es:edi],"I"
- jne @@No_BLASTER
- inc edi
-
- mov al,[byte es:edi]
- sub al,"0"
- mov [byte init_settings.IRQ_no],al
- call @@skip
- cmp [byte es:edi],"D"
- jne @@No_BLASTER
- inc edi
- mov al,[byte es:edi]
- sub al,"0"
- mov [byte init_settings.DMA_no],al
- call @@skip
- cmp [byte es:edi],"T"
- jne @@No_BLASTER
- inc edi
- cmp [byte es:edi],"1"
- je @@set_SB
- cmp [byte es:edi],"2"
- je @@set_SB
- cmp [byte es:edi],"3"
- je @@set_SB
- cmp [byte es:edi],"4"
- je @@set_SBPRO
- stc
- pop es
- ret
- @@set_SB:
- mov [byte init_settings.card_type],SB_CARD
- clc
- pop es
- ret
- @@set_SBPRO:
- mov [byte init_settings.card_type],SBPRO_CARD
- clc
- pop es
- ret
- @@No_SBstring:
- xor al,al ; scan environment for next ZERO
- mov ecx,400h
- repne scasb
- and ecx,ecx
- jz @@No_BLASTER
- cmp [byte es:edi],0 ; if double zeros then finished
- jnz @@SrchEnvrLoop
- @@No_BLASTER:
- stc
- pop es
- ret
- @@blaster_string:
- db "BLASTER="
- proc @@skip
- inc edi
- @@back_skip:
- cmp [byte es:edi]," "
- jne @@done_skip
- inc edi
- jmp @@back_skip
- @@done_skip:
- ret
- endp
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; cy = not detected ;
- ; cn = detected ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB_detect
- mov eax,[dword init_settings.PORT_no]
- mov [dword SB_BASE],0
- mov [dword SB_MIXER],4h
- mov [dword SB_RESET],6h
- mov [dword SB_READ_DATA],0ah
- mov [dword SB_WRITE_DATA],0ch
- mov [dword SB_DATA_AVAIL],0eh
- mov [dword SB_DATA_AVAIL16],0fh
- add [dword SB_BASE],eax
- add [dword SB_MIXER],eax
- add [dword SB_RESET],eax
- add [dword SB_READ_DATA],eax
- add [dword SB_WRITE_DATA],eax
- add [dword SB_DATA_AVAIL],eax
- add [dword SB_DATA_AVAIL16],eax
-
- lea eax,[DACi_freq_convert]
- mov [dword CARD_freq_convert],eax
- lea eax,[DACi_volume_convert]
- mov [dword CARD_volume_convert],eax
-
- mov al,1
- mov edx,[dword SB_RESET]
- out dx,al
- in al,dx
- in al,dx
- in al,dx
- in al,dx
- xor al,al
- mov edx,[dword SB_RESET]
- out dx,al
- mov cl,64h
- @@DataWait:
- mov edx,[dword SB_DATA_AVAIL]
- in al,dx
- test al,80h
- jnz @@YesData
- dec cl
- jnz @@DataWait
- jmp @@exit
- @@YesData:
- mov edx,[dword SB_READ_DATA]
- in al,dx
- cmp al,0AAh
- je @@YepSB
- dec cl
- jnz @@DataWait
- jmp @@exit
- @@YepSB:
- clc
- ret
- @@exit:
- stc
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- label SB_sample_settings tDAC_ssetings
- tDAC_ssetings <11025,00222,222,11200>
- tDAC_ssetings <16538,00332,332,16538>
- tDAC_ssetings <22050,00442,442,22050>
- tDAC_ssetings <33075,00662,662,33075>
- tDAC_ssetings <44100,00882,882,44100>
-
- proc SB_init_compatable
- mov eax,offset SB_trig_compatable
- mov [SB_trig],eax
-
- movzx eax,[byte init_settings.DAC_Samplerate]
- mov ecx,size tDAC_ssetings
- mul ecx
-
- mov [byte DAC_shift_value],7
- mov ebx,[dword eax+SB_sample_settings.DAC_sr]
- mov [dword DAC_sampling_rate],ebx
- mov ebx,[dword eax+SB_sample_settings.DAC_mix_buffer_size]
- mov [dword DAC_mix_buffer_size],ebx
- mov ebx,[dword eax+SB_sample_settings.DMA_length]
- mov [dword DMA_length],ebx
- mov eax,[dword eax+SB_sample_settings.DMA_real_sr]
- push eax
- mov bl,[byte init_settings.IRQ_no]
- lea edx,[SB_virtualmixxer]
- mov cx,cs
- call setirqvector
- xor edx,edx ;set sampling rate
- mov eax,1000000
- pop ecx
- div ecx
- neg al
- push eax
- mov al,40h ;TIME_CONSTANT
- call SB_write_dac
- pop eax
- call SB_write_dac
- mov al,0D1h ;SPEAKER_ON
- call SB_write_dac
- cli
- in al,21h
- mov bl,1
- mov cl,[byte init_settings.IRQ_no]
- shl bl,cl
- not bl
- and al,bl
- out 21h,al
- mov al,01011000b ;DMA remote-init
- mov ah,[byte init_settings.DMA_no]
- mov ebx,[dword DAC_PHYSICAL_PAGE]
- mov ecx,[dword DMA_length]
- dec ecx
- call DMA_setup
- call SB_trig_compatable
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- label SBPRO_sample_settings tDAC_ssetings ; NB/ SBPRO can't do more than 22050
- tDAC_ssetings <11025,00222,0444,23000>
- tDAC_ssetings <16538,00332,0664,35000>
- tDAC_ssetings <22050,00442,0884,88200>
- tDAC_ssetings <22050,00442,0884,88200>
- tDAC_ssetings <22050,00442,0884,88200>
-
- proc sb_init_advanced
- mov eax,offset SB_trig_advanced
- mov [SB_trig],eax
-
- movzx eax,[byte init_settings.DAC_Samplerate]
- mov ecx,size tDAC_ssetings
- mul ecx
- cmp [byte init_settings.card_type],SBPRO_CARD
- je @@set_for_SBPRO
- mov [byte DAC_shift_value],7
- mov ebx,[dword eax+SB_sample_settings.DAC_sr]
- mov [dword DAC_sampling_rate],ebx
- mov ebx,[dword eax+SB_sample_settings.DAC_mix_buffer_size]
- mov [dword DAC_mix_buffer_size],ebx
- mov [DAC_double_buf2],ebx
- mov ebx,[dword eax+SB_sample_settings.DMA_length]
- mov [dword DMA_length],ebx
- mov eax,[dword eax+SB_sample_settings.DMA_real_sr]
- push eax
- mov bl,[byte init_settings.IRQ_no]
- lea edx,[SB_virtualmixxer]
- mov cx,cs
- call setirqvector
- xor edx,edx ;set sampling rate
- mov eax,256000000
- pop ecx
- div ecx
- mov ebx,0ffffh
- sub ebx,eax
- shr ebx,8
- push ebx
- jmp @@done_set
- @@set_for_SBPRO:
- push eax
- mov [byte DAC_shift_value],6
- ;-SETUP_PRO MIXXER SETTINGS---------
- mov eax,00000h ;reset mixxer first
- call SB_write_mixer
- mov eax,0020eh
- call SB_write_mixer
- mov eax,0ff22h ;set Master volume
- call SB_write_mixer
- mov eax,0ff04h ;set DSP volume
- call SB_write_mixer
- ;-SETUP_PRO MIXXER SETTINGS---------
- pop eax
- mov ebx,[dword eax+SBPRO_sample_settings.DAC_sr]
- mov [dword DAC_sampling_rate],ebx
- mov ebx,[dword eax+SBPRO_sample_settings.DAC_mix_buffer_size]
- mov [dword DAC_mix_buffer_size],ebx
- lea ebx,[ebx*2]
- mov [DAC_double_buf2],ebx
- mov ebx,[dword eax+SBPRO_sample_settings.DMA_length]
- mov [dword DMA_length],ebx
- mov eax,[dword eax+SBPRO_sample_settings.DMA_real_sr]
- push eax
- mov bl,[byte init_settings.IRQ_no]
- lea edx,[SBPRO_virtualmixxer]
- mov cx,cs
- call setirqvector
- xor edx,edx ;set sampling rate
- mov eax,256000000
- pop ecx
- div ecx
- mov ebx,0ffffh
- sub ebx,eax
- shr ebx,8
- push ebx
- @@done_set:
- mov al,40h ;TIME_CONSTANT
- call SB_write_dac
- pop eax
- call SB_write_dac
- mov al,0D1h ;SPEAKER_ON
- call SB_write_dac
- cli
- in al,21h
- mov bl,1
- mov cl,[byte init_settings.IRQ_no]
- shl bl,cl
- not bl
- and al,bl
- out 21h,al
- mov al,01011000b ;DMA remote-init
- mov ah,[byte init_settings.DMA_no]
- mov ebx,[dword DAC_PHYSICAL_PAGE]
- mov ecx,[dword DMA_length]
- lea ecx,[ecx*2]
- dec ecx
- call DMA_setup
- mov al,48h ;DMA_8_BIT_DAC (FAST)
- call SB_write_dac
- mov eax,[dword DMA_length]
- dec eax
- call SB_write_dac
- mov al,ah
- call SB_write_dac
- mov al,91h
- call SB_write_dac
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB08_init
- mov bl,[byte init_settings.IRQ_no]
- call getirqvector
- mov [dword DAC_old_irq_ofs],edx
- mov [word DAC_old_irq_sel],cx
-
- cmp [byte init_settings.card_type],SB_CARD
- je @@set_advanced
- cmp [byte init_settings.card_type],SBPRO_CARD
- je @@set_advanced
- cmp [byte init_settings.card_type],SB15EM_CARD
- je @@set_compatable
- ret
- @@set_compatable:
- call sb_init_compatable
- ret
- @@set_advanced:
- call sb_init_advanced
- ret
- endp
-
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; SB1.X, SB2,0 + SBPRO deinit ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc sbsub1_deinit
- mov bl,1
- mov cl,[byte init_settings.IRQ_no]
- shl bl,cl
- in al,21h
- or al,bl
- out 21h,al
- mov bl,[byte init_settings.IRQ_no]
- mov edx,[dword DAC_old_irq_ofs]
- mov cx,[word DAC_old_irq_sel]
- call setirqvector
- ret
- endp
-
- proc SB08_deinit
- call SB_detect
- cmp [byte init_settings.card_type],SBPRO_CARD
- jne @@dont_reset
- mov eax,110eh ;set for mono
- call SB_write_mixer
- @@dont_reset:
- mov al,0D0h ;HALT_DMA
- call SB_write_dac
- cli
- call sbsub1_deinit
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- label SB16_sample_settings tDAC_ssetings
- tDAC_ssetings <11025,00222,0444,011400>
- tDAC_ssetings <16538,00332,0664,017400>
- tDAC_ssetings <22050,00442,0884,088200>
- tDAC_ssetings <33075,00662,1324,165000>
- tDAC_ssetings <44100,00882,1764,176400>
-
- proc SB16_init
- mov bl,[byte init_settings.IRQ_no]
- call getirqvector
- mov [dword DAC_old_irq_ofs],edx
- mov [word DAC_old_irq_sel],cx
- mov bl,[byte init_settings.IRQ_no]
- lea edx,[SB16_virtualmixxer]
- mov cx,cs
- call setirqvector
- mov [byte DAC_shift_value],6
- movzx eax,[byte init_settings.DAC_Samplerate]
- mov ecx,size tDAC_ssetings
- mul ecx
- mov ebx,[dword eax+SB16_sample_settings.DAC_sr]
- mov [dword DAC_sampling_rate],ebx
- mov ebx,[dword eax+SB16_sample_settings.DAC_mix_buffer_size]
- mov [dword DAC_mix_buffer_size],ebx
- lea ebx,[ebx*4]
- mov [DAC_double_buf2],ebx
- mov ebx,[dword eax+SB16_sample_settings.DMA_length]
- mov [dword DMA_length],ebx
- mov eax,[dword eax+SB16_sample_settings.DMA_real_sr]
- push eax
- mov bl,[byte init_settings.IRQ_no]
- lea edx,[SB16_virtualmixxer]
- mov cx,cs
- call setirqvector
- cli
- in al,21h
- mov bl,1
- mov cl,[byte init_settings.IRQ_no]
- shl bl,cl
- not bl
- and al,bl
- out 21h,al
- mov al,01011000b
- mov ah,[byte init_settings.DMA_no]
- mov ebx,[dword DAC_PHYSICAL_PAGE]
- mov ecx,[dword DMA_length]
- lea ecx,[ecx*4]
- dec ecx
- call DMA_setup
- mov al,41h
- call SB_write_dac
- pop eax
- xchg al,ah
- call SB_write_dac
- mov al,ah
- call SB_write_dac
- mov al,0b6h
- call SB_write_dac
- mov al,030h
- call SB_write_dac
- mov eax,[dword DMA_length]
- dec eax
- call SB_write_dac
- mov al,ah
- call SB_write_dac
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SB16_deinit
- cli
- mov al,0d9h
- call SB_write_dac
- call sbsub1_deinit
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; GUS DEPENDANT CODE ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;GUS CONST
- GUS_irq_table db 0,0,1,2,0,3,0,4,0,0,0,5,6,0,0,7
- GUS_dma_table db 0,1,0,2,0,3,4,5
-
- ;Gravis only
- gus_base dd 0
- gus_status dd 6
- gus_timercontrol dd 8
- gus_timerdata dd 9
- gus_irqdmacontrol dd 0bh
- gus_midictrl dd 100h
- gus_mididata dd 101h
- gus_voice dd 102h
- gus_command dd 103h
- gus_datalo dd 104h
- gus_datahi dd 105h
- gus_GF1_status dd 106h
- gus_dram dd 107h
- DMA_state db ?
-
- gus_volume_table:
- db 020h,040h,060h,080h,090h,094h,098h,09ch
- db 0A0h,0A2h,0A4h,0A6h,0A8h,0AAh,0ACh,0AEh
- db 0B0h,0B1h,0B2h,0B3h,0B4h,0B5h,0B6h,0B7h
- db 0B8h,0B9h,0BAh,0BBh,0BCh,0BDh,0BEh,0BFh
- db 0C0h,0C0h,0C1h,0C1h,0C2h,0C2h,0C3h,0C3h
- db 0C4h,0C4h,0C5h,0C5h,0C6h,0C6h,0C7h,0C7h
- db 0C8h,0C8h,0C9h,0C9h,0CAh,0CAh,0CBh,0CBh
- db 0CCh,0CCh,0CDh,0CDh,0CEh,0CEh,0CFh,0CFh
- db 0D0h,0D0h,0D0h,0D0h,0D1h,0D1h,0D1h,0D1h
- db 0D2h,0D2h,0D2h,0D2h,0D3h,0D3h,0D3h,0D3h
- db 0D4h,0D4h,0D4h,0D4h,0D5h,0D5h,0D5h,0D5h
- db 0D6h,0D6h,0D6h,0D6h,0D7h,0D7h,0D7h,0D7h
- db 0D8h,0D8h,0D8h,0D8h,0D9h,0D9h,0D9h,0D9h
- db 0DAh,0DAh,0DAh,0DAh,0DBh,0DBh,0DBh,0DBh
- db 0DCh,0DCh,0DCh,0DCh,0DDh,0DDh,0DDh,0DDh
- db 0DEh,0DEh,0DEh,0DEh,0DFh,0DFh,0DFh,0DFh
- db 0E0h,0E0h,0E0h,0E0h,0E0h,0E1h,0E1h,0E1h
- db 0E1h,0E2h,0E2h,0E2h,0E2h,0E3h,0E3h,0E3h
- db 0E3h,0E4h,0E4h,0E4h,0E4h,0E5h,0E5h,0E5h
- db 0E5h,0E6h,0E6h,0E6h,0E6h,0E7h,0E7h,0E7h
- db 0E7h,0E8h,0E8h,0E8h,0E8h,0E9h,0E9h,0E9h
- db 0E9h,0EAh,0EAh,0EAh,0EAh,0EAh,0EBh,0EBh
- db 0EBh,0EBh,0ECh,0ECh,0ECh,0ECh,0EDh,0EDh
- db 0EDh,0EDh,0EEh,0EEh,0EEh,0EEh,0EFh,0EFh
- db 0EFh,0EFh,0F0h,0F0h,0F0h,0F0h,0F1h,0F1h
- db 0F1h,0F1h,0F2h,0F2h,0F2h,0F2h,0F3h,0F3h
- db 0F3h,0F3h,0F4h,0F4h,0F4h,0F4h,0F4h,0F5h
- db 0F5h,0F5h,0F5h,0F6h,0F6h,0F6h,0F6h,0F6h
- db 0F7h,0F7h,0F7h,0F7h,0F8h,0F8h,0F8h,0F8h
- db 0F9h,0F9h,0F9h,0F9h,0F9h,0F9h,0FAh,0FAh
- db 0FAh,0FAh,0FBh,0FBh,0FBh,0FBh,0FBh,0FBh
- db 0FBh,0FCh,0FCh,0FCh,0FCh,0FCh,0FCh,0FCh
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; GUS Code ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUSi_freq_convert
- mov eax,[dword edi+tfunk_chan.rfreq]
- xor edx,edx
- mov ecx,43
- div ecx
- mov [dword edi+tfunk_chan.CARD_freq],eax
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUSi_volume_convert
- xor eax,eax
- cmp [byte edi+tfunk_chan.channel_kill],STOP
- je @@transt
- mov al,[byte funk_info.master_volume]
- cmp al,0
- je @@transt
- xor ecx,ecx
- mov cl,[byte edi+tfunk_chan.rvolume]
- inc al
- mul ecx
- shr eax,4
- @@transt:
- mov al,[byte eax+gus_volume_table]
- mov [byte edi+tfunk_chan.CARD_volume],al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; GUS interface routines ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_set_freq
- mov edx,[dword gus_command]
- mov al,1
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.CARD_freq]
- out dx,ax
- ret
- endp
-
- ; cl = volume to set
- proc GUS_set_volume
- cmp cl,[byte gus_volume_table]
- jae @@cont
- ret
- @@cont:
- mov edx,[dword gus_command]
- MOV al,89h
- OUT dx,al
- INC edx
- IN ax,dx
- mov bl,ah
- cmp bl,4
- jae @@dont_level1
- mov bl,4
- @@dont_level1:
- xor ch,ch
- cmp bl,cl
- je @@end
- jb @@set_ramp_to_up
- mov ch,040h
- xchg bl,cl
- @@set_ramp_to_up:
- ;bl = ramp start
- ;cl = ramp end
- ;ch = ramp direction
- DEC edx
- MOV al,0dh
- OUT dx,al
- ADD edx,2
- MOV al,3
- OUT dx,al
- SUB edx,2
- MOV al,7
- OUT dx,al
- ADD edx,2
- MOV al,bl
- OUT dx,al
- SUB edx,2
- MOV al,8
- OUT dx,al
- ADD edx,2
- mov al,cl
- OUT dx,al
- SUB edx,2
- MOV al,6
- OUT dx,al
- ADD edx,2
- MOV al,3fh
- OUT dx,al
- sub edx,2
- MOV al,0dh
- OUT dx,al
- ADD edx,2
- MOV al,ch
- OUT dx,al
- @@loopramp:
- sub edx,2
- mov al,8dh
- out dx,al
- add edx,2
- in al,dx
- test al,1
- jz @@loopramp
- @@end:
- ret
- endp
-
- proc GUS_load_channel
- mov cl,[byte gus_volume_table]
- call GUS_set_volume
- mov edx,[dword gus_command]
- xor al,al
- out dx,al
- add edx,2
- mov al,3
- out dx,al
- cmp [byte init_settings.card_type],GUS_FIXB_CARD
- je @@no_varbalance
- sub edx,2
- mov al,0ch
- out dx,al
- add edx,2
- mov al,[byte edi+tfunk_chan.balance]
- shr al,4
- out dx,al
- @@no_varbalance:
- call GUS_set_freq
- mov edx,[dword gus_command]
- ;Send sample begin
- mov al,0ah
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.CARD_sample_ptr]
- add eax,32
- shr eax,7
- out dx,ax
- dec edx
- mov al,0bh
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.CARD_sample_ptr]
- add eax,32
- shl eax,9
- out dx,ax
- dec edx
- ;Send sample start
- mov al,2
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.start]
- add eax,32
- shr eax,7
- out dx,ax
- dec edx
- mov al,3
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.start]
- add eax,32
- shl eax,9
- out dx,ax
- dec edx
- ;Send sample end
- mov al,4
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.length]
- sub eax,32
- shr eax,7
- out dx,ax
- dec edx
- mov al,5
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.length]
- sub eax,32
- shl eax,9
- out dx,ax
- mov cl,[byte edi+tfunk_chan.CARD_volume]
- call GUS_set_volume
- ret
- endp
-
- proc GUS_set_start
- mov edx,[dword gus_command]
- ;Send sample start
- mov al,2
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.start]
- add eax,32
- shr eax,7
- out dx,ax
- dec edx
- mov al,3
- out dx,al
- inc edx
- mov eax,[dword edi+tfunk_chan.start]
- add eax,32
- shl eax,9
- out dx,ax
- ret
- endp
-
- proc GUS_fire_channel
- cmp [dword edi+tfunk_chan.length],64
- jae @@cont
- ret
- @@cont:
- mov edx,[dword gus_command]
- xor al,al
- out dx,al
- test [byte edi+tfunk_chan.funkctrl],1b
- jz @@dont_loop
- mov al,8
- @@dont_loop:
- add edx,2
- out dx,al
- mov [byte edi+tfunk_chan.funkctrl],0
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_update
- lea edi,[funk_chan1]
- xor cl,cl
- @@play_slot:
- push ecx
- mov al,cl
- mov edx,[dword gus_voice]
- out dx,al
- test [byte edi+tfunk_chan.funkctrl],10b
- jnz @@fire_channel
- call GUS_set_freq
- mov cl,[byte edi+tfunk_chan.CARD_volume]
- call GUS_set_volume
- test [byte edi+tfunk_chan.funkctrl],10000000b
- jz @@done
- and [byte edi+tfunk_chan.funkctrl],01111111b
- call GUS_set_start
- jmp @@done
- @@fire_channel:
- call GUS_load_channel
- @@done:
- pop ecx
- add edi,size tfunk_chan
- inc cl
- cmp cl,8
- jb @@play_slot
-
- lea edi,[funk_chan1]
- xor cl,cl
- @@play_slot2:
- mov al,cl
- mov edx,[dword gus_voice]
- out dx,al
- test [byte edi+tfunk_chan.funkctrl],10b
- jz @@done2
- call GUS_fire_channel
- @@done2:
- add edi,size tfunk_chan
- inc cl
- cmp cl,8
- jb @@play_slot2
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_mixxer
- cld
- push ds
- mov ds,[word cs:DATA32_sel]
- pushad
- push es
- mov es,[word DATA32_sel]
- @@next_irq:
- mov edx,[dword gus_status]
- in al,dx
- mov [byte @@irq_state],al
- test [byte @@irq_state],10000000b
- jnz @@DMA_interrupt
- call funk_tracker
- call GUS_update
- mov edx,[dword gus_command]
- mov al,45h
- out dx,al
- add edx,2
- xor al,al
- out dx,al
- mov al,8
- out dx,al
- jmp @@end
- @@DMA_interrupt:
- mov edx,[dword gus_command]
- mov al,041h
- out dx,al
- add edx,2
- in al,dx
- or [byte DMA_state],1
- test [byte @@irq_state],11101111b
- jz @@next_irq
- @@end:
- mov al,20h
- out 20h,al
- out 0a0h,al
- pop es
- popad
- pop ds
- iretd
- @@irq_state:
- db ?
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;this routine is from Adam's DOS32 libraries ;
- ; ;
- ; IN: nothing ;
- ; OUT: Carry is set if couldn't find environment or it has invalid ;
- ; settings. ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_env
- push es
- mov es,[word Zero_SEL]
- mov ah,62h ; Get the PSP segment
- int 21h
- movzx edi,bx
- shl edi,4
- movzx edi,[word es:edi+2Ch] ; Get the Environment segment value
- shl edi,4
- cld
- mov ecx,10000h
- @@SrchEnvrLoop:
- lea esi,[@@ultrasnd_string]
- mov ecx,9
- repe cmpsb
- jne @@No_GUSstring
- mov [byte init_settings.card_type],GUS_VARB_CARD
- mov ebx,[es:edi] ;OK, Found the string 'ULTRASND='
- mov eax,ebx ;check for the valid paramters
- and ebx,0ffff00ffh
- cmp ebx,02C300032h ;'2x0,'
- jne @@No_ULTRASND
- shr eax,8
- call @@get_digit ;eeax = char digit in al
- mov edx,eax ;load port address
- shl edx,4
- add edx,200h
- sub al,1h ;port must be between 210h .. 260h
- cmp al,5h
- ja @@No_ULTRASND
- mov [dword init_settings.PORT_no],edx
- add edi,4
- xor ecx,ecx
- movzx eax,[byte es:edi]
- call @@get_digit
- cmp [byte eax+GUS_dma_table],0
- je @@No_ULTRASND
- mov [byte init_settings.DMA_no],al ;get playback DMA
- inc edi
- cmp [byte es:edi],','
- jne @@No_ULTRASND
- inc edi
- movzx eax,[byte es:edi]
- call @@get_digit
- cmp [byte eax+GUS_dma_table],0
- je @@No_ULTRASND
- mov [byte init_settings.DMA_no2],al ;DMA record channel
- inc edi
- cmp [byte es:edi],','
- jne @@No_ULTRASND
- xor ebx,ebx
- inc edi
- cmp [byte es:edi],'1'
- jne @@J61
- mov bl,10
- inc edi
- @@J61:
- mov eax,[es:edi]
- call @@get_digit
- add al,bl
- cmp al,15
- ja @@No_ULTRASND
- cmp [byte eax+GUS_irq_table],0
- je @@No_ULTRASND
- mov BL,AL
- mov [byte init_settings.IRQ_no],al
- inc edi
- cmp [byte es:edi],','
- jne @@No_ULTRASND
- inc edi
- cmp [byte es:edi],'1'
- jne @@J62
- mov BH,10
- inc edi
- @@J62:
- mov al,[es:edi]
- call @@get_digit
- add al,bh
- cmp al,15
- ja @@No_ULTRASND
- cmp [byte eax+GUS_irq_table],0
- je @@No_ULTRASND
- mov [byte init_settings.IRQ_no2],al ;MIDI irq number
- inc edi
- cmp [byte es:edi],','
- je @@got_it
- cmp [byte es:edi],' '
- je @@got_it
- cmp [byte es:edi],0
- jne @@No_ULTRASND
- @@got_it:
- clc
- pop es
- ret
- @@No_GUSstring:
- mov al,0 ; scan environment for next ZERO
- mov ecx,400h
- repne scasb
- and ecx,ecx
- jz @@No_ULTRASND
- cmp [byte es:edi],0 ; if double zeros then finished
- jnz @@SrchEnvrLoop
- @@No_ULTRASND:
- stc
- pop es
- ret
- @@get_digit:
- sub al,'0'
- jc @@No_digi
- cmp al,9
- ja @@No_digi
- movzx eax,al
- ret 0
- @@No_digi:
- add esp,4 ; ignore pushed EIP
- stc
- pop es
- ret
- @@ULTRASND_string:
- db 'ULTRASND='
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc gus_delay
- mov edx,[dword gus_dram]
- in al,dx
- in al,dx
- in al,dx
- in al,dx
- in al,dx
- in al,dx
- in al,dx
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; esi ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_mem_in
- mov edx,[dword gus_command]
- mov al,43h
- out dx,al
- inc edx
- mov eax,esi
- out dx,ax
- dec edx
- mov al,44h
- out dx,al
- add edx,2
- mov eax,esi
- shr eax,16
- out dx,al
- add edx,2
- in al,dx
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; edi ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_mem_out
- push eax
- mov edx,[dword gus_Command]
- mov al,43h
- out dx,al
- inc edx
- mov eax,edi
- out dx,ax
- dec edx
- mov al,44h
- out dx,al
- add edx,2
- mov eax,edi
- shr eax,16
- out dx,al
- add edx,2
- pop eax
- out dx,al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; cy = not detected ;
- ; cn = detected ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_detect
- mov eax,[dword init_settings.PORT_no]
- add [dword gus_base],eax
- add [dword gus_Status],eax
- add [dword gus_timercontrol],eax
- add [dword gus_timerdata],eax
- add [dword gus_irqdmacontrol],eax
- add [dword gus_midictrl],eax
- add [dword gus_mididata],eax
- add [dword gus_voice],eax
- add [dword gus_Command],eax
- add [dword gus_DataLo],eax
- add [dword gus_DataHi],eax
- add [dword gus_GF1_status],eax
- add [dword gus_dram],eax
- lea eax,[GUSi_freq_convert]
- mov [dword CARD_freq_convert],eax
- lea eax,[GUSi_volume_convert]
- mov [dword CARD_volume_convert],eax
- mov edx,[dword gus_command]
- mov al,4Ch
- out dx,al
- add edx,2
- xor al,al
- out dx,al
- call gus_Delay
- call gus_Delay
- mov edx,[dword gus_command]
- mov al,4Ch
- out dx,al
- add edx,2
- mov al,1
- out dx,al
- mov al,0AAh
- xor edi,edi
- call gus_mem_out
- mov edi,100h
- mov al,55h
- call gus_mem_out
- xor esi,esi
- call gus_mem_in
- push eax
- mov edx,[dword gus_command]
- mov al,4Ch
- out dx,al
- add edx,2
- mov al,1
- out dx,al
- pop eax
- cmp al,0AAh
- jnz @@Nope
- clc
- ret
- @@Nope:
- stc
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_find_mem
- xor bl,bl
- mov edi,100h
- @@fm_loop:
- mov al,0AAh
- call GUS_mem_out
- mov ecx,0FFFFh
- @@bw_loop:
- nop
- dec ecx
- jnz @@bw_loop
- mov esi,edi
- call GUS_mem_in
- cmp al,0AAh
- jnz @@exit
- add edi,40000h
- inc bl
- cmp bl,4
- jbe @@fm_loop
- @@exit:
- sub edi,100h
- jz @@standard
- mov [dword sample_memory_lim],edi
- ret
- @@standard:
- mov [dword sample_memory_lim],40000h
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; NB/this 'total reset' routine is from adam's dos32 routines ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_total_reset
- cmp [byte init_settings.IRQ_no],0
- je @@zero_irq1
- movzx edx,[byte init_settings.IRQ_no]
- mov dl,[byte edx+GUS_irq_table]
- or dl,dl
- jz @@invalid_setting
- @@Zero_irq1:
- mov [byte @@irq_control],dl
- movzx edx,[byte init_settings.IRQ_no2]
- or dl,dl
- jz @@Zero_irq2
- mov dl,[byte edx+GUS_irq_table]
- or dl,dl
- jz @@invalid_setting
- shl dl,3
- @@Zero_irq2:
- or [byte @@irq_control],dl
- mov al,[byte init_settings.IRQ_no]
- cmp al,[byte init_settings.IRQ_no2]
- jne @@diff_irqs
- cmp [byte init_settings.IRQ_no],0
- je @@diff_irqs
- and [byte @@irq_control],0111b
- or [byte @@irq_control],40h
- @@diff_irqs:
- movzx edx,[byte init_settings.DMA_no]
- or dl,dl
- jz @@Zero_dma2
- mov dl,[byte edx+GUS_dma_table]
- or dl,dl
- jz @@invalid_setting
- @@Zero_dma1:
- mov [byte @@dma_control],dl
- movzx edx,[byte init_settings.DMA_no2]
- or dl,dl
- jz @@Zero_dma2
- mov dl,[byte edx+GUS_dma_table]
- or dl,dl
- jz @@invalid_setting
- shl dl,3
- @@Zero_dma2:
- or [byte @@dma_control],dl
- mov al,[byte init_settings.DMA_no]
- cmp al,[byte init_settings.DMA_no2]
- jne @@diff_dmas
- and cl,cl
- jz @@diff_irqs
- and [byte @@dma_control],0111b
- or [byte @@dma_control],40h
- @@diff_dmas:
- cli
- mov ecx,200h
- loop $
- mov edx,[dword GUS_base]
- add edx,0fh
- mov al,5
- out dx,al
- mov edx,[dword GUS_base]
- mov al,00001011b
- out dx,al
- mov edx,[dword GUS_irqdmacontrol]
- xor al,al
- out dx,al
- mov edx,[dword GUS_base]
- add edx,0fh
- xor al,al
- out dx,al
- mov edx,[dword GUS_base]
- mov al,00001011b
- out dx,al
- mov edx,[dword GUS_irqdmacontrol]
- mov al,[byte @@dma_control]
- or al,80h
- out dx,al
- mov edx,[dword GUS_base]
- mov al,01001011b
- out dx,al
- mov edx,[dword gus_irqdmacontrol]
- mov al,[byte @@irq_control]
- out dx,al
- mov edx,[dword GUS_base]
- mov al,00001011b
- out dx,al
- mov edx,[dword gus_irqdmacontrol]
- mov al,[byte @@dma_control]
- out dx,al
- mov edx,[dword GUS_base]
- mov al,01001011b
- out dx,al
- mov edx,[dword gus_irqdmacontrol]
- mov al,[byte @@irq_control]
- out dx,al
- mov edx,[dword gus_voice]
- xor al,al
- out dx,al
- mov edx,[dword GUS_base]
- mov al,0001001b
- out dx,al
- mov edx,[dword gus_voice]
- xor al,al
- out dx,al
- in al,0A1h
- mov ah,al
- in al,21h
- mov cl,[byte init_settings.IRQ_no]
- cmp cl,2
- jne @@j3
- mov cl,9
- @@j3:
- mov ebx,1
- shl ebx,cl
- not ebx
- and eax,ebx
- mov cl,[byte init_settings.IRQ_no2]
- cmp cl,2
- jne @@j4
- mov cl,9
- @@j4:
- mov ebx,1
- shl ebx,cl
- not ebx
- and eax,ebx
- out 021h,al
- mov al,ah
- out 0A1h,al
- ;part II
- mov edx,[dword gus_command]
- mov al,04Ch
- out dx,al
- add edx,2
- mov al,00000000b
- out dx,al
- mov ecx,10
- @@J56:
- call gus_delay
- loop @@J56
- mov edx,[dword gus_command]
- mov al,04Ch
- out dx,al
- add edx,2
- mov al,00000001b
- out dx,al
- mov ecx,10
- @@J57:
- call gus_delay
- loop @@J57
- mov edx,[dword gus_midictrl]
- mov al,00000011b
- out dx,al
- mov ecx,10
- @@J58:
- call gus_delay
- loop @@J58
- xor al,al
- out dx,al
- mov edx,[dword gus_command]
- mov al,041h
- out dx,al
- add edx,2
- xor al,al
- out dx,al
- mov edx,[dword gus_command]
- mov al,045h
- out dx,al
- add edx,2
- xor al,al
- out dx,al
- mov edx,[dword gus_command]
- mov al,049h
- out dx,al
- add edx,2
- xor al,al
- out dx,al
- mov edx,[dword gus_command]
- mov al,049h
- out dx,al
- add edx,2
- xor al,al
- out dx,al
- mov edx,[dword gus_command]
- mov al,0eh
- out dx,al
- add edx,2
- mov al,13 or 0C0h
- out dx,al
- mov edx,[dword gus_GF1_status]
- in al,dx
- mov edx,[dword gus_command]
- mov al,041h
- out dx,al
- add edx,2
- in al,dx
- mov edx,[dword gus_command]
- mov al,049h
- out dx,al
- add edx,2
- in al,dx
- @@ClrFIFO:
- mov edx,[dword gus_command]
- mov al,08fh
- out dx,al
- add edx,2
- in al,dx
- and al,11000000b
- cmp al,11000000b
- jne @@ClrFIFO
- xor bl,bl
- @@stop_loop:
- mov edx,[dword GUS_voice]
- mov al,bl
- out dx,al
- mov edx,[dword gus_command]
- xor al,al
- out dx,al
- add edx,2
- xor al,al
- out dx,al
- mov edx,[dword gus_command]
- xor al,al
- out dx,al
- add edx,2
- mov al,10b
- out dx,al
- mov edx,[dword gus_command]
- mov al,0dh
- out dx,al
- add edx,2
- mov al,10b
- out dx,al
- mov edx,[dword gus_command]
- mov al,09h
- out dx,al
- inc edx
- movzx eax,[byte gus_volume_table]
- shl eax,8
- out dx,ax
- call gus_delay
- inc bl
- cmp bl,14
- jb @@stop_loop
- mov edx,[dword gus_GF1_status]
- in al,dx
- mov edx,[dword gus_command]
- mov al,041h
- out dx,al
- add edx,2
- in al,dx
- mov edx,[dword gus_command]
- mov al,049h
- out dx,al
- add edx,2
- in al,dx
- @@Clr2FIFO:
- mov edx,[dword gus_command]
- mov al,08fh
- out dx,al
- add edx,2
- in al,dx
- and al,11000000b
- cmp al,11000000b
- jne @@Clr2FIFO
- mov edx,[dword gus_command]
- mov al,0eh
- out dx,al
- add edx,2
- mov al,13 or 0C0h
- out dx,al
- mov edx,[dword gus_command]
- mov al,04ch
- out dx,al
- add edx,2
- mov al,00000111b
- out dx,al
- sti
- @@invalid_setting:
- ret
- @@dma_control:
- db ?
- @@irq_control:
- db ?
- @@gf1:
- db ?
- @@midi:
- db ?
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_reset
- ;added code
- mov edx,[dword gus_base]
- mov al,0bh
- out dx,al
- ;added code
- mov ebx,[dword gus_Command]
- mov ecx,[dword gus_DataHi]
- mov edx,ebx
- mov al,4Ch
- out dx,al
- mov edx,ecx
- xor al,al
- out dx,al
- call gus_delay
- call gus_delay
- mov edx,ebx
- mov al,4Ch
- out dx,al
- mov edx,ecx
- mov al,1
- out dx,al
- call gus_delay
- call gus_delay
- mov edx,ebx
- mov al,41h
- out dx,al
- mov edx,ecx
- xor al,al
- out dx,al
- mov edx,ebx
- mov al,45h
- out dx,al
- mov edx,ecx
- xor al,al
- out dx,al
- mov edx,ebx
- mov al,49h
- out dx,al
- mov edx,ecx
- xor al,al
- out dx,al
- mov edx,ebx
- mov al,0Eh
- out dx,al
- add edx,2
- mov al,13
- or al,0Ch
- out dx,al
- mov edx,[dword gus_Status]
- in al,dx
- mov edx,ebx
- mov al,41h
- out dx,al
- mov edx,ecx
- in al,dx
- mov edx,ebx
- mov al,49h
- out dx,al
- mov edx,ecx
- in al,dx
- mov edx,ebx
- mov al,8Fh
- out dx,al
- mov edx,ecx
- in al,dx
- push ebx ecx
- xor ecx,ecx
- mov bl,0
- @@VoiceClearLoop:
- mov edx,[dword gus_Voice]
- mov al,cl
- out dx,al
- inc edx
- xor al,al
- out dx,al
- add edx,2
- mov al,3
- out dx,al
- sub edx,2
- mov al,0Dh
- out dx,al
- add edx,2
- mov al,3
- out dx,al
- sub edx,2
- mov al,0ch
- out dx,al
- add edx,2
- mov al,bl
- out dx,al
- sub edx,2
- mov al,09h
- out dx,al
- inc edx
- movzx eax,[byte gus_volume_table]
- shl eax,8
- out dx,ax
- xor bl,0ffh
- inc ecx
- cmp ecx,13
- jnz @@VoiceClearLoop
- pop ecx ebx
- mov edx,ebx
- mov al,41h
- out dx,al
- mov edx,ecx
- in al,dx
- mov edx,ebx
- mov al,49h
- out dx,al
- mov edx,ecx
- in al,dx
- mov edx,ebx
- mov al,8Fh
- out dx,al
- mov edx,ecx
- in al,dx
- mov edx,ebx
- mov al,4Ch
- out dx,al
- mov edx,ecx
- mov al,7
- out dx,al
- ;added code
- mov edx,ebx
- mov al,4Ch
- out dx,al
- mov edx,ecx
- mov al,7
- out dx,al
- ;;;;
- mov edx,[dword gus_base] ;set irq
- mov al,4bh
- out dx,al
- movzx eax,[byte init_settings.IRQ_no]
- mov al,[byte eax+GUS_irq_table]
- push eax
- MOV edx,[dword gus_irqdmacontrol]
- OUT dx,AL
- ;;;;
- mov edx,[dword gus_base] ;set dma
- mov al,0bh
- out dx,al
- movzx eax,[byte init_settings.DMA_no]
- mov al,[byte eax+GUS_dma_table]
- MOV edx,[dword gus_irqdmacontrol]
- OUT dx,AL
- ;;;;
- mov edx,[dword gus_base] ;set irq
- mov al,4bh
- out dx,al
- MOV edx,[dword gus_irqdmacontrol]
- pop eax
- OUT dx,AL
- ;;;;
- mov edx,[dword gus_base]
- mov al,0bh
- out dx,al
- mov edx,ebx
- mov al,41h
- out dx,al
- mov edx,ecx
- xor al,al
- out dx,al
- mov edx,ebx
- mov al,45h
- out dx,al
- mov edx,ecx
- xor al,al
- out dx,al
- mov edx,ebx
- mov al,49h
- out dx,al
- mov edx,ecx
- xor al,al
- out dx,al
- MOV AL,80h
- MOV edx,[dword gus_timerdata]
- OUT dx,AL
- xor al,al
- MOV edx,[dword gus_timerdata]
- OUT dx,AL
- mov edx,[dword gus_base]
- mov al,0bh
- out dx,al
- ;added code
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; GUS Interrupt ready ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_intready
- cli
- mov edx,[dword gus_command]
- mov al,45h
- out dx,al
- mov al,2bh
- and al,0f7h
- mov edx,[dword gus_datahi]
- out dx,al
- xor al,al
- out 021h,al
- xor al,al
- out 0a1h,al
- mov al,20h
- out 020h,al
- mov al,20h
- out 0a0h,al
- mov al,47h
- mov edx,[dword gus_command]
- out dx,al
- mov al,195 ;<<-speed
- add edx,2
- out dx,al
- sub edx,2
- mov al,45h
- out dx,al
- add edx,2
- mov al,8
- out dx,al
- mov edx,[dword gus_timercontrol]
- mov al,4
- out dx,al
- mov edx,[dword gus_timerdata]
- mov al,2
- out dx,al
- mov al,8
- mov edx,[dword gus_base]
- out dx,al
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; GUS Save INT timer registers ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc GUS_init
- mov bl,[byte init_settings.IRQ_no]
- call getirqvector
- mov [dword DAC_old_irq_ofs],edx
- mov [word DAC_old_irq_sel],cx
-
- mov bl,[byte init_settings.IRQ_no]
- lea edx,[GUS_mixxer]
- mov ecx,cs
- call setirqvector
- call GUS_total_reset
- call GUS_find_mem
- call GUS_reset
- call GUS_intready
- ret
- endp
-
- proc GUS_deinit
- call GUS_reset
- mov bl,[byte init_settings.IRQ_no]
- mov edx,[dword DAC_old_irq_ofs]
- mov cx,[word DAC_old_irq_sel]
- call setirqvector
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; esi trans mem ;
- ; edi gus mem locatin ;
- ; ecx bytes to trans ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc gus_upload
- cli
- mov edx,[dword gus_Command]
- @@MainLoop:
- mov edx,[dword gus_Command]
- mov al,44h
- out dx,al
- add edx,2
- mov eax,edi
- shr eax,16
- out dx,al
- mov edx,[dword gus_Command]
- mov al,43h
- out dx,al
- inc edx
- mov eax,edi
- out dx,ax
- mov edx,[dword gus_dram]
- outsb
- inc edi
- dec ecx
- jnz @@MainLoop
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; edi trans mem ;
- ; esi gus mem locatin ;
- ; ecx bytes to trans ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc gus_dnload
- cli
- mov edx,[dword gus_Command]
- @@MainLoop:
- mov edx,[dword gus_Command]
- mov al,44h
- out dx,al
- add edx,2
- mov eax,esi
- shr eax,16
- out dx,al
- mov edx,[dword gus_Command]
- mov al,43h
- out dx,al
- inc edx
- mov eax,esi
- out dx,ax
- mov edx,[dword gus_dram]
- insb
- inc esi
- dec ecx
- jnz @@MainLoop
- sti
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; PAS DEPENDANT CODE ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc PAS16_virtualmixxer
- cld
- push ds es
- pushad
- mov ax,[word cs:DATA32_sel]
- mov ds,ax
- mov es,ax
- mov edx,INTRCTLRST ;clear the interrupt
- xor edx,[_MVTranslateCode] ;xlate the board address
- in al,dx
- test al,bISsampbuff+bISsamprate ;our interrupt?
- jz @@exit_int
- out dx,al ;yes, flush it...
- mov esi,[dword DAC_mix_buffer]
- mov edx,[dword DAC_mix_buffer_right]
- mov edi,[dword DAC_mix_buffer2]
- add edi,[DAC_double_buf1]
- mov eax,[DAC_double_buf1]
- xchg eax,[DAC_double_buf2]
- mov [DAC_double_buf1],eax
- mov ecx,[dword DAC_mix_buffer_size]
- xor ebx,ebx
- @@trans16:
- mov eax,[edx+ebx]
- shl eax,16
- mov ax,[word esi+ebx]
- mov [edi+ebx*2],eax
- add ebx,2
- dec ecx
- jnz @@trans16
- call funk_tracker
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- mov edi,[dword DAC_mix_buffer]
- xor eax,eax
- rep stosd
- mov ecx,[dword DAC_mix_buffer_size]
- shr ecx,1
- mov edi,[dword DAC_mix_buffer_right]
- rep stosd
- lea ebx,[funk_chan1]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan2]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan3]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan4]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan5]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan6]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- lea ebx,[funk_chan7]
- mov edi,[dword DAC_mix_buffer]
- call DAC_channel_mixxer
- lea ebx,[funk_chan8]
- mov edi,[dword DAC_mix_buffer_right]
- call DAC_channel_mixxer
- @@exit_int:
- mov al,20h ;clear the interrupt
- cmp [init_settings.IRQ_no],8 ;2nd IRQ controller?
- jb @@F1
- out 0A0h,al
- @@F1:
- out 020h,al
- popad
- pop es ds
- iretd
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Pro Audio routines for FunkTracker ;
- ; ;
- ; Routines from Media Vision SDK, Inc. ;
- ; Copyright (c) 1991,1992. All Rights Res. ;
- ; ;
- ; Converted to P-mode by Jason Nunn ;
- ; ;
- ; This INIT code that talks to MVSOUND.SYS isn't supposed to run in P-mode;
- ; So, problems _may_ occur. I'll replace it when i get time. ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ; Hardware associated with the PAS1/PAS2/CDPC
- DEFAULT_BASE = 00388h ;default base I/O address
- ALT_BASE_1 = 00384h ;first alternate address
- ALT_BASE_2 = 0038Ch ;second alternate address
- ALT_BASE_3 = 00288h ;third alternate address
- USE_ACTIVE_ADDR = 00000h ;uses what is currently active
- AUDIOFILT = 00B8Ah ;Audio Filter Control Register
- INTRCTLRST = 00B89h ;Interrupt Control Status Register
- INTRCTLR = 00B8Bh ;Interrupt Control Register write
- CROSSCHANNEL = 00F8Ah ;Cross Channel Register
- SAMPLERATE = 01388h ;(t0) Sample Rate Timer Register
- SAMPLECNT = 01389h ;(t1) Sample Count Register
- TMRCTLR = 0138Bh ;Local Timer Control Register
- ; Factory Default Settings
- DEFAULTDMA = 1 ;DMA channel 1
- DEFAULTIRQ = 7 ;IRQ channel 7
- DEFAULTINT = 65h ;Interrupt # for software interface
- ; mixer select
- OUTPUTMIXER = 00h ;output mixer H/W select
- INPUTMIXER = 40h ;input mixer select
- DEFMIXER = -1 ;use last mixer selected
- MIXERMAX = 1fh ;maximum mixer setting
- MVVOLUMEMAX = 3fh ;MVA508 maximum mixer setting
- NSVOLUMEMAX = 28h ;National maximum mixer setting
- EQUALIZERMAX = 0ch ;maximum equalizer setting
- EQUALIZERMID = 06h ;maximum mid setting
- ; Filter register bits
- fFIdatabits = 00011111B ;filter select and decode field bits
- fFImutebits = 00100000B ;filter mute field bits
- fFIpcmbits = 11000000B ;filter sample rate field bits
- bFImute = 00100000B ;filter mute bit
- bFIsrate = 01000000B ;filter sample rate timer mask
- bFIsbuff = 10000000B ;filter sample buffer counter mask
- FILTERMAX = 6 ;six possible settings
- ; Cross Channel Bit definitions
- fCCcrossbits = 00001111B ;; cross channel bit field
- fCCpcmbits = 11110000B ;; pcm/dma control bit field
- bCCr2r = 00000001B ;; CROSSCHANNEL Right to Right
- bCCl2r = 00000010B ;; CROSSCHANNEL Left to Right
- bCCr2l = 00000100B ;; CROSSCHANNEL Right to Right
- bCCl2l = 00001000B ;; CROSSCHANNEL Left to Left
- bCCdac = 00010000B ;; DAC/ADC Control
- bCCmono = 00100000B ;; PCM Monaural Enable
- bCCenapcm = 01000000B ;; Enable PCM state machine
- bCCdrq = 10000000B ;; Enable DRQ bit
- ; Interrupt Control Register Bits
- fICintmaskbits = 00011111B ;; interrupt mask field bits
- fICrevbits = 11100000B ;; revision mask field bits
- bICsamprate = 00000100B ;; Sample Rate timer interrupt enable
- bICsampbuff = 00001000B ;; Sample buffer timer interrupt enable
- fICrevshr = 5 ;; rotate rev bits to lsb
-
-
- ;Interrupt Status Register Bits
-
- fISints = 1fh ; Interrupt bit field
- bISleftfm = 01h ; Left FM interrupt active
- bISritfm = 02h ; Right FM interrupt active
- bISsamprate = 04h ; Sample Rate timer interrupt active
- bISsampbuff = 08h ; Sample buffer timer interrupt active
- bISmidi = 10h ; MIDI interrupt active
- bISPCMlr = 20h ; PCM left/right active
- bISActive = 40h ; Hardware is active (not in reset)
- bISClip = 80h ; Sample Clipping has occured
-
- MASTERCHIPR = 0ff88h ;; Master Chip Rev (r)
- ENHANCEDSCSI = 07f89h ;; Enhanced SCSI detect port
- SYSCONFIG2 = 08389h ;; System Config 2 (r/w)
- COMPATREGE = 0f788h ;; Compatible Rgister Enable (r/w)
- MASTERMODRD = 0ff8bh ;; Master Mode Read (r)
- SLAVEMODRD = 0ef8bh ;; Slave Mode Read (r)
- ; Sys Config 2
- bSC216bit = 00000100b ;; 16 bit audio
- bSC212bit = 00001000b ;; 12 bit interleaving (d2 must be set too)
- ; I/O Config 3
- bIC3pcmint = 00001111b ;; pcm IRQ channel select
- bIC3cdint = 11110000b ;; cd IRQ channel select
- ; Compatibility Register
- cpMPUEmulation = 00000001b ;; MPU emuation is on bit
- ; Slave Mode Read
- bSMRDdrvtyp = 00000011b ;; drive interface type
- bSMRDfmtyp = 00000100b ;; FM chip type
- bSMRDdactyp = 00001000b ;; 16 bit dac (1) or 8 bit dac (0)
- ; Master Mode Read
- bMMRDatps2 = 00000001b ;; AT(1) or PS2(0) bus
- bMMRDmsmd = 00000100b ;; master/slave mode
- ; Interrupt Controller #1 Port Addresses and Interrupt Masks
- IRQ1MASKREG = 021h ;; 8259 mask register
- INT7MSK = 10000000B ;; interrupt 7 mask
- ; Interrupt Controller #2 Port Addresses and Interrupt Masks
- IRQ2MASKREG = 0A1h ;; 8259 mask register
- ;; dma controller #1 port addresses
- DMAC0ADDR = 000h ;; DMA channel 0 Base & Current Address
- DMAC0COUNT = 001h ;; DMA channel 0 Base & Current Count
- DMAC1ADDR = 002h ;; DMA channel 1 Base & Current Address
- DMAC1COUNT = 003h ;; DMA channel 1 Base & Current Count
- DMAC2ADDR = 004h ;; DMA channel 2 Base & Current Address
- DMAC2COUNT = 005h ;; DMA channel 2 Base & Current Count
- DMAC3ADDR = 006h ;; DMA channel 3 Base & Current Address
- DMAC3COUNT = 007h ;; DMA channel 3 Base & Current Count
- DMA2C4ADDR = 0C0h ;; DMA channel 4 Base & Current Address
- DMA2C4COUNT = 0C2h ;; DMA channel 4 Base & Current Count
- DMA2C5ADDR = 0C4h ;; DMA channel 5 Base & Current Address
- DMA2C5COUNT = 0C6h ;; DMA channel 5 Base & Current Count
- DMA2C6ADDR = 0C8h ;; DMA channel 6 Base & Current Address
- DMA2C6COUNT = 0CAh ;; DMA channel 6 Base & Current Count
- DMA2C7ADDR = 0CCh ;; DMA channel 7 Base & Current Address
- DMA2C7COUNT = 0CEh ;; DMA channel 7 Base & Current Count
- DMARDSTAT = 008h ;; DMA read status
- DMAWRCNTRL = 008h ;; DMA write command register
- DMAWREQ = 009h ;; DMA write request register
- DMAWRSMR = 00Ah ;; DMA write single mask register
- DMAWRMODE = 00Bh ;; DMA write mode register
- DMACLEAR = 00Ch ;; DMA clear low/high flip-flop
- DMARDTEMP = 00Dh ;; DMA read temp register
- DMAWRCLR = 00Dh ;; DMA write master clear
- DMACLRMSK = 00Eh ;; DMA clear mask register
- DMAWRALL = 00Fh ;; DMA write all mask register bits
- DMA2RDSTAT = 0D0h ;; DMA read status
- DMA2WRCNTRL = 0D0h ;; DMA write command register
- DMA2WREQ = 0D2h ;; DMA write r=est register
- DMA2WRSMR = 0D4h ;; DMA write single mask register
- DMA2WRMODE = 0D6h ;; DMA write mode register
- DMA2CLEAR = 0D8h ;; DMA clear low/high flip-flop
- DMA2RDTEMP = 0DAh ;; DMA read temp register
- DMA2WRCLR = 0DAh ;; DMA write master clear
- DMA2CLRMSK = 0DCh ;; DMA clear mask register
- DMA2WRALL = 0DEh ;; DMA write all mask register bits
- CH0PAGEREG = 087h ;; Channel 0 Page Register
- CH1PAGEREG = 083h ;; Channel 1 Page Register
- CH2PAGEREG = 081h ;; Channel 2 Page Register
- CH3PAGEREG = 082h ;; Channel 3 Page Register
- CH5PAGEREG = 08Bh ;; Channel 5 Page Register
- CH6PAGEREG = 089h ;; Channel 6 Page Register
- CH7PAGEREG = 08Ah ;; Channel 7 Page Register
-
- struc MVState
- _sysspkrtmr db 0 ; 42 System Speaker Timer Address
- _systmrctlr db 0 ; 43 System Timer Control
- _sysspkrreg db 0 ; 61 System Speaker Register
- _joystick db 0 ; 201 Joystick Register
- _lfmaddr db 0 ; 388 Left FM Synth Address
- _lfmdata db 0 ; 389 Left FM Synth Data
- _rfmaddr db 0 ; 38A Right FM Synth Address
- _rfmdata db 0 ; 38B Right FM Synth Data
- _dfmaddr db 0 ; 788 Dual FM Synthesizer Address Register
- _dfmdata db 0 ; 789 Dual FM Synthesizer Data Register
- db 0 ; reserved for future use
- _paudiomixr db 0 ; 78B Paralllel Audio Mixer Control
- _audiomixr db 0 ; B88 Audio Mixer Control
- _intrctlrst db 0 ; B89 Interrupt Status
- _audiofilt db 0 ; B8A Audio Filter Control
- _intrctlr db 0 ; B8B Interrupt Control
- _pcmdata db 0 ; F88 PCM Data I/O Register
- _RESRVD2 db 0 ; reserved
- _crosschannel db 0 ; F8A Cross Channel
- _RESRVD3 db 0 ; reserved
- _samplerate dw 0 ; 1388 Sample Rate Timer
- _samplecnt dw 0 ; 1389 Sample Count Register
- _spkrtmr dw 0 ; 138A Shadow Speaker Timer Count
- _tmrctlr db 0 ; 138B Shadow Speaker Timer Control
- _mdirqvect db 0 ; 1788 MIDI IRQ Vector Register
- _mdsysctlr db 0 ; 1789 MIDI System Control Register
- _mdsysstat db 0 ; 178A MIDI IRQ Status Register
- _mdirqclr db 0 ; 178B MIDI IRQ Clear Register
- _mdgroup1 db 0 ; 1B88 MIDI Group #1 Register
- _mdgroup2 db 0 ; 1B89 MIDI Group #2 Register
- _mdgroup3 db 0 ; 1B8A MIDI Group #3 Register
- _mdgroup4 db 0 ; 1B8B MIDI Group #4 Register
- ends
-
- bMVA508 = 0000000000000001b ; MVA508(1) or National(0)
- bMVPS2 = 0000000000000010b ; PS2 bus stuff
- bMVSLAVE = 0000000000000100b ; CDPC Slave device is present
- bMVSCSI = 0000000000001000b ; SCSI interface
- bMVENHSCSI = 0000000000010000b ; Enhanced SCSI interface
- bMVSONY = 0000000000100000b ; Sony 535 interface
- bMVDAC16 = 0000000001000000b ; 16 bit DAC
- bMVSBEMUL = 0000000010000000b ; SB h/w emulation
- bMVMPUEMUL = 0000000100000000b ; MPU h/w emulation
- bMVOPL3 = 0000001000000000b ; OPL3(1) or 3812(0)
- bMV101 = 0000010000000000b ; MV101 ASIC
- bMV101_REV = 0111100000000000b ; MV101 Revision
- bMV101_MORE = 1000000000000000b ; more bits in BX
- ;; Define the ASIC versions
- ASIC_VERSION_B = 0000000000000010b ; revision B
- ASIC_VERSION_C = 0000000000000011b ; revision C
- ASIC_VERSION_D = 0000000000000100b ; revision D
- ASIC_VERSION_E = 0000000000000101b ; revision E
- ASIC_VERSION_F = 0000000000000110b ; revision F
- ;; First Pro Audio Spectrum feature list
- PRODUCT_PROAUDIO = bMVSCSI
- ;; Pro Audio Plus feature list
- PRODUCT_PROPLUS = bMV101+bMVSCSI+bMVENHSCSI+bMVSBEMUL+bMVOPL3
- ;; Pro Audio Spectrum 16 feature list
- PRODUCT_PRO16 = bMV101+bMVA508+bMVSCSI+bMVENHSCSI+bMVSBEMUL+bMVDAC16+bMVOPL3
- ;; CDPC feature list
- PRODUCT_CDPC = bMV101+bMVSLAVE+bMVSONY+bMVSBEMUL+bMVDAC16+bMVOPL3
- ;; Set each one to zero - to be init later if selected
- PROAS100 = 0
- PROAS200 = 0
- PROAS300 = 0
- CDPC = 0
- PRODUCTDEFINED = 0 ; to be set if a product is selected
- _MVTranslateCode dd 0 ; I/O base xor default_base
- _MVHWVersionBits dw -1 ; holds the product feature bits
- VERSION_PAS = 0 ; Pro Audio Spectrum
- VERSION_PASPLUS = 1 ; Pro Audio Plus card
- VERSION_PAS16 = 2 ; Pro Audio 16 card
- VERSION_CDPC = 3 ; CDPC card & unit
- ; The following equates build up a mask of bits that we do wish to keep
- ; when comparing feature bits. The zero bits can be ignored, whereas, the
- ; the 1 bits must match.
- PASdocare = bMVA508 OR bMVDAC16 OR bMVOPL3 OR bMV101
- PASPLUSdocare = bMVA508 OR bMVDAC16 OR bMVOPL3 OR bMV101
- PAS16docare = bMVA508 OR bMVDAC16 OR bMVOPL3 OR bMV101
- CDPCdocare = bMVA508 OR bMVDAC16 OR bMVOPL3 OR bMV101
- label MVProductIDTable
- dw PRODUCT_PROAUDIO and PASdocare
- dw PRODUCT_PROPLUS and PASPLUSdocare
- dw PRODUCT_PRO16 and PAS16docare
- dw PRODUCT_CDPC and CDPCdocare
- dw -1
- label MVDoCareBits
- dw PASdocare
- dw PASPLUSdocare
- dw PAS16docare
- dw CDPCdocare
- dw -1
-
- struc dmaaddr
- _dmach db ? ; DMA channel selected
- _dmardstat db ? ; DMA read status
- _dmawrcntrl db ? ; DMA write command register
- _dmawreq db ? ; DMA write request register
- _dmawrsmr db ? ; DMA write single mask register
- _dmawrmode db ? ; DMA write mode register
- _dmaclear db ? ; DMA clear low/high flip-flop
- _dmardtemp db ? ; DMA read temp register
- _dmawrclr db ? ; DMA write master clear
- _dmaclrmsk db ? ; DMA clear mask register
- _dmawrall db ? ; DMA write all mask register bits
- ends
-
- MVOurDMAPageReg dw CH1PAGEREG ; default to DMA channel 1 page reg
- MVOurDMAddress dw DMAC1ADDR ; default to DMA channel 1 address reg
- label DMA1AddrTable
- db DEFAULTDMA ; DMA channel selected
- db DMARDSTAT ; DMA read status
- db DMAWRCNTRL ; DMA write command register
- db DMAWREQ ; DMA write request register
- db DMAWRSMR ; DMA write single mask register
- db DMAWRMODE ; DMA write mode register
- db DMACLEAR ; DMA clear low/high flip-flop
- db DMARDTEMP ; DMA read temp register
- db DMAWRCLR ; DMA write master clear
- db DMACLRMSK ; DMA clear mask register
- db DMAWRALL ; DMA write all mask register bits
- ; table of address pointers to the various DMA 2 addresses
- label DMA2AddrTable
- db DEFAULTDMA ; DMA channel selected
- db DMA2RDSTAT ; DMA read status
- db DMA2WRCNTRL; DMA write command register
- db DMA2WREQ ; DMA write request register
- db DMA2WRSMR ; DMA write single mask register
- db DMA2WRMODE ; DMA write mode register
- db DMA2CLEAR ; DMA clear low/high flip-flop
- db DMA2RDTEMP ; DMA read temp register
- db DMA2WRCLR ; DMA write master clear
- db DMA2CLRMSK ; DMA clear mask register
- db DMA2WRALL ; DMA write all mask register bits
- PCM_DMAPointer dd offset DMA1AddrTable ;default to channel 1 table
- MVTheIRQMask db INT7MSK ;8259 interrupt mask
- MVSampleSize db 2 ;sample size: 0=8,1=12,2=16
- mvhwShadowPointer dd 0 ;points to the start of the data table
- MVHardwareShadowTable MVState <>
- MVTypeOfSetup db 0 ;polled/dma interrupt masks & stuff..
- mvStatusWord dw 0 ;Holds current status:
- ; 0 = inactive, available
- ; 1 = currently playing
- ; 2 = currently recording
- DMAMASK = bICsampbuff ;dma mask
- POLLEDMASK = bICsamprate+bICsampbuff ;polled mask
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc PCM_pause
- jmp @@j
- @@j:
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Given a specific I/O address, this routine will see if the ;
- ; hardware exists at this address. ;
- ; ;
- ; Entry Conditions: ;
- ; DI holds the I/O address to test ;
- ; BX:CX = bMVSCSI ;
- ; ;
- ; Exit Conditions: ;
- ; BX:CX = the bit fields that identify the board ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SearchHWVersion
- ; calculate the translation code
- xor edi,DEFAULT_BASE
- mov eax,0BC00H ;make sure MVSOUND.SYS is loaded
- mov ebx,'??' ;this is our way of knowing if the
- xor ecx,ecx ;hardware is actually present.
- xor edx,edx
- int 2fh ;get the ID pattern
- xor bx,cx ;build the result
- xor bx,dx
- cmp bx,'MV' ;if not here, exit...
- jnz @@sehw_bad
- ; get the MVSOUND.SYS specified DMA and IRQ channel
- mov eax,0bc04h ;get the DMA and IRQ numbers
- int 2fh
- mov [init_settings.DMA_no],bl ;save the correct DMA & IRQ
- mov [init_settings.IRQ_no],cl
- ; grab the version # in the interrupt mask. The top few bits hold the version #
- mov edx,INTRCTLR ;board ID is in MSB 3 bits
- xor edx,edi
- in al,dx
- cmp al,-1 ;bus float meaning not present?
- je @@sehw_bad ;yes, there is no card here
- mov ah,al
- xor al,fICrevbits
- out dx,al
- call PCM_pause
- call PCM_pause
- in al,dx
- cmp al,ah
- xchg al,ah
- out dx,al
- jnz @@sehw_bad ;we have a bogus board
- and ax,fICrevbits ;isolate the ID bits & clear AH
- mov cl,fICrevshr ;shift the bits into a meaningful
- shr al,cl ;position (least signficant bits)
- movzx esi,ax ;save the version #
- ; We do have hardware! Load the product bit definitions
- sub ebx,ebx
- mov ecx,bMVSCSI ;setup bx:cx for the original PAS
- or al,al ;is this the first version of h/w?
- jz @@sehw_done ;yes, simple exit will do.
- ; Checks the installed hardware for all the feature bits. ;
- ; All second generation Pro Audio cards use the MV101 and have SB emulation.
- or ecx,bMVSBEMUL+bMV101 ;force SB emulation
- ; determine if the enhanced SCSI interface is present
- mov edx,ENHANCEDSCSI ;test for SCSI mod (U48)
- xor edx,edi ;modify via the translate code
- out dx,al ;strobe
- call PCM_pause ;I/O bus delay
- in al,dx ;get the bit
- and al,1 ; bit0==1 means old SCSI PAL
- cmp al,1 ;reverse sense
- sbb eax,eax ;ax = ffff if enhanced SCSI
- and eax,bMVENHSCSI
- or ecx,eax
- ; determine AT/PS2, CDPC slave mode
- mov edx,MASTERMODRD
- xor edx,edi
- in al,dx
- test al,bMMRDatps2 ;AT(1) or PS2(0)
- jnz @@F1
- or ecx,bMVPS2
- @@F1:
- test al,bMMRDmsmd ;Master(0) or Slave(1)
- jz @@F2
- or ecx,bMVSLAVE
- @@f2:
- push ecx
- mov edx,MASTERCHIPR
- xor edx,edi
- in al,dx
- and ax,000Fh
- mov cl,11
- shl eax,cl
- pop ecx
- or ecx,eax
- ; determine the CDROM drive type, FM chip, 8/16 bit DAC, and mixer
- mov edx,SLAVEMODRD
- xor edx,edi
- in al,dx
- test al,bSMRDdactyp ;16 bit DAC?
- jz @@F3 ;no, its an 8 bit DAC
- or ecx,bMVDAC16 ;its a 16 bit DAC
- @@f3:
- test al,bSMRDfmtyp ;OPL3 chip?
- jz @@F4 ;no, so it's the PAS16 card
- or ecx,bMVOPL3 ;is an OPL3
- @@f4:
- mov edx,ecx ;inference check for new mixer
- and edx,bMVSLAVE+bMVDAC16 ;Slave & 16 bit dac is the CDPC
- cmp edx,bMVDAC16 ;16 bit DAC on master?
- jnz @@F5 ;no, it's the CDPC with Nation mixer
- or ecx,bMVA508
- @@f5:
- and al,bSMRDdrvtyp ;isolate the CDROM drive type
- cmp al,2 ;Sony 535 interface?
- jnz @@F6 ;no, continue on...
- and ecx,NOT (bMVSCSI+bMVENHSCSI) ;yes, flush the SCSI bits
- or ecx,bMVSONY ;set the 535 bit
- @@f6:
- ; determine if MPU-401 emulation is active
- mov edx,COMPATREGE ;compatibility register
- xor edx,edi
- in al,dx
- test al,cpMPUEmulation
- jz @@sehw_done
- or ecx,bMVMPUEMUL
- @@sehw_done:
- ; loop on a table search to find identify the board
- push ebx
- mov ebx,-2
- @@sehw_05:
- add ebx,2
- cmp [word ebx+MVProductIDTable],-1
- jz @@sehw_bad_hw ;yes, we can't identify this board
- mov edx,ecx
- and dx,[word ebx+MVDoCareBits]
- cmp dx,[word ebx+MVProductIDTable]
- jnz @@sehw_05
- mov edx,ebx
- shr edx,1
- pop ebx
- movzx edi,di
- mov [dword _MVTranslateCode],edi
- mov eax,esi
- sub ah,ah ;for our purposes, we will return SCSI
- xchg ah,al ;into ah
- clc ;The board was identified !.
- mov [_mvHWVersionBits],cx
- jmp @@sehw_exit
- @@sehw_bad_hw:
- pop ebx
- stc
- jmp @@sehw_exit
- @@sehw_bad:
- stc
- @@sehw_exit:
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Detects and identifies the installed Pro AudioSuctrum. ;
- ; ;
- ; Entry Conditions: ;
- ; edi = word address containing the base address. ;
- ; ;
- ; Exit Conditions: ;
- ; Carry is set on error ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc mvGetHWVersion
- lea eax,[DACi_freq_convert]
- mov [dword CARD_freq_convert],eax
- lea eax,[DACi_volume_convert]
- mov [dword CARD_volume_convert],eax
-
- or edi,edi
- jnz @@mvgehw_05
- mov edi,DEFAULT_BASE
- call SearchHWVersion
- jnc @@mvgehw_exit
- mov edi,ALT_BASE_1
- call SearchHWVersion
- jnc @@mvgehw_exit
- mov edi,ALT_BASE_2
- call SearchHWVersion
- jnc @@mvgehw_exit
- mov edi,ALT_BASE_3
- @@mvgehw_05:
- call SearchHWVersion
- @@mvgehw_exit:
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Initializes the state table pointer. ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc MVInitStatePtr
- ; setup a pointer to our local hardware state table
- lea ebx,[MVHardwareShadowTable]
- mov [dword mvhwShadowPointer],ebx
- mov [ebx+MVState._audiomixr],31h ;lowest filter setting
- mov [ebx+MVState._crosschannel],09h ;cross channel l-2-l, r-2-r
- ; find the int 2F interface and if found, use it's state table pointer
- mov ax,0BC00h ;MVSOUND.SYS ID check
- mov bx,'??'
- sub cx,cx
- sub dx,dx
- int 2fh
- xor bx,cx
- xor bx,dx
- cmp bx,'MV'
- jnz @@imvsp_done ;no, exit home
- mov ax,0BC02H ;get the pointer
- int 2fh
- cmp ax,'MV'
- jnz @@imvsp_done
- movzx edx,dx
- movzx ebx,bx
- shl edx,4
- add edx,ebx
- sub edx,[dword CODE32_addr]
- mov [dword mvhwShadowPointer],edx
- @@imvsp_done:
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Turn off the PCM timers, interrupts, and state machine. ;
- ; ;
- ; Entry Conditions: ;
- ; ;
- ; Exit Conditions: ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc StopPCM
- push edi
- mov edi,[mvhwShadowPointer]
- ; clear the audio filter sample bits
- mov edx,AUDIOFILT
- xor edx,[_MVTranslateCode]
- cli
- mov al,[edi+MVState._audiofilt] ;get the state
- and al,not (bFIsrate+bFIsbuff) ;flush the sample timer bits
- mov [edi+MVState._audiofilt],al ;save the new state
- out dx,al
- ; clear the PCM enable bit
- mov al,[edi+MVState._crosschannel] ;get the current cross channel
- and al,not bCCenapcm ;clear the PCM enable bit
- or al,bCCdac
- mov edx,CROSSCHANNEL
- xor edx,[_MVTranslateCode]
- out dx,al ; end to the hardware
- mov [edi+MVState._crosschannel],al
- ; disable the 16 bit stuff
- test [_MVHWVersionBits],bMV101 ;101 chip?
- jz @@stpc02 ;no, don't touch this...
- mov edx,SYSCONFIG2
- xor edx,[_MVTranslateCode]
- in al,dx
- and al,not bSC216bit+bSC212bit ;flush the 16 bit stuff
- out dx,al
- @@stpc02:
- ; clear the appropriate Interrupt Control Register bit
- mov ah,[MVTypeOfSetup]
- and ah,bICsamprate+bICsampbuff
- not ah
- mov edx,INTRCTLR
- xor edx,[_MVTranslateCode]
- in al,dx
- and al,ah ;kill sample timer interrupts
- out dx,al
- mov [edi+MVState._intrctlr],al
- ; clear the system interrupt mask only if no other ints are used
- test al,fICintmaskbits XOR (bICsamprate+bICsampbuff)
- jnz @@stpc10
- ; select the correct IRQ controller, then mask it...
- cmp [init_settings.IRQ_no],2 ;Chained IRQ channel?
- jz @@stpc10 ;yes, leave it open...
- mov dx,IRQ1MASKREG
- cmp [init_settings.IRQ_no],8 ;2nd IRQ controller?
- jl @@stpc05
- mov dl,IRQ2MASKREG
- @@stpc05:
- in al,dx
- or al,[MVTheIRQMask]
- out dx,al
- sti
- @@stpc10:
- push edi
- cmp [mvStatusWord],0 ;is there any activity?
- jz @@kidm_none
- mov edi,[PCM_DMAPointer] ;get the DMA pointer
- sub dx,dx ;clear out the high byte
- ; mask out the DMA to stop it
- cli
- mov al,[edi+dmaaddr._dmach] ;get the adjusted dma channel #
- or al,0100b ;disable the DMA
- mov dl,[edi+dmaaddr._dmawrsmr]
- out dx,al
- ; remove control on the DRQ line
- mov edi,[mvhwShadowPointer]
- mov al,[edi+mvstate._crosschannel] ;get the state
- mov edx,CROSSCHANNEL
- xor edx,[_MVTranslateCode] ;xlate the board address
- and al,not bCCdrq ;clear the DRQ bit
- out dx,al
- mov [edi+mvstate._crosschannel],al ;and save the new state
- sti
- @@kidm_none:
- pop edi
- mov [mvStatusWord],0
- pop edi
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Initializes the PCM code ;
- ; ;
- ; Entry Conditions: ;
- ; None ;
- ; ;
- ; Exit Conditions: ;
- ; AX = Version of this Code ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc InitPCM
- mov [MVTypeOfSetup],POLLEDMASK ;flushes both interrupts
- ;for upcoming calls
- movsx eax,[byte init_settings.DMA_no] ;initialize the DMA now...
- and eax,0111b
- mov ebx,eax
- shl ebx,1
- jnz @@seldma_02
- push sp
- pop cx
- cmp cx,sp
- jnz @@seldma_bad
- @@seldma_02:
- mov dx,[ebx+@@dmatable]
- or dx,dx
- jz @@seldma_bad
- mov [init_settings.DMA_no],al
- mov [byte MVOurDMAPageReg],dh
- mov [byte MVOurDMAddress],dl
- lea ebx,[DMA1AddrTable]
- cmp al,4
- jl @@seldma_05
- lea ebx,[DMA2AddrTable]
- sub al,4
- @@seldma_05:
- mov [ebx+dmaaddr._dmach],al
- mov [dword PCM_DMAPointer],ebx
- sub ax,ax
- @@seldma_bad:
- mov eax,[dword DAC_old_irq_ofs]
- or eax,eax
- jz @@F1
- mov bl,[init_settings.IRQ_no]
- mov edx,[dword DAC_old_irq_ofs]
- mov cx,[word DAC_old_irq_sel]
- call setirqvector
- mov [dword DAC_old_irq_ofs],0
- mov [word DAC_old_irq_sel],0
- @@F1:
-
- sub ax,ax
- movsx ecx,[init_settings.IRQ_no] ;initialize the IRQ now... ;get the irq # (2-7,10-12,14-15)
- and cl,0fh ;save only the valid bits
- mov bx,01
- shl bx,cl
- and bx,1001110010111100b
- jz @@seirqbad
- mov [init_settings.IRQ_no],cl
- cmp cl,8 ;2nd interrupt controller?
- jb @@F3 ;no, skip
- xchg bh,bl
- @@f3:
- mov [mvTheIRQMask],bl
-
- mov eax,[DAC_old_irq_ofs]
- or eax,eax
- jnz @@F2
-
- mov bl,[init_settings.IRQ_no]
- call getirqvector
- mov [dword DAC_old_irq_ofs],edx
- mov [word DAC_old_irq_sel],cx
- @@F2:
- mov ax,1
- @@seirqbad:
- dec ax
- call StopPCM ;kill the Audio Spectrum board
- mov edx,INTRCTLRST ;flush any pending PCM irq
- xor edx,[_MVTranslateCode] ;xlate the board address
- out dx,al
- ret
- label @@dmatable
- dw (CH0PAGEREG SHL 8) + DMAC0ADDR
- dw (CH1PAGEREG SHL 8) + DMAC1ADDR
- dw (CH2PAGEREG SHL 8) + DMAC2ADDR
- dw (CH3PAGEREG SHL 8) + DMAC3ADDR
- dw 0
- dw (CH5PAGEREG SHL 8) + DMA2C5ADDR
- dw (CH6PAGEREG SHL 8) + DMA2C6ADDR
- dw (CH7PAGEREG SHL 8) + DMA2C7ADDR
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;
- ; LoadDMA -- Load the DMA controller to read/write data to the MV board
- ;
- ; Entry Conditions:
- ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc LoadDMA
- mov edi,[mvhwShadowPointer]
- mov esi,[PCM_DMAPointer] ;point to the DMA controller table
- sub dx,dx ;clear out the high byte
- ; kill the dma until all programming is done
- mov al,[esi+dmaaddr._dmach] ;get the adjusted dma channel #
- or al,0100b ;causes all DMA to be suspended
- mov dl,[esi+dmaaddr._dmawrsmr]
- out dx,al
- ; program the mode
- mov al,01011000b ;01011000b ;get the app's desired mode
- or al,[esi+dmaaddr._dmach] ;merge the adjusted dma channel #
- mov dl,[esi+dmaaddr._dmawrmode]
- out dx,al
- ; adjust the address for a 16 bit channel
-
- mov eax,[dword DAC_PHYSICAL_PAGE]
- push eax
- shr eax,16
- ; setup the page register
- mov dx,[MVOurDMAPageReg]
- out dx,al
- mov bl,al
- ; reset the flip-flop, then output the address, then count
- mov dl,[esi+dmaaddr._dmaclear] ;dh is still clear...
- out dx,al ;flush...
- pop eax
- cmp esi,offset DMA1AddrTable ;1st DMA controller?
- jz @@F1 ;yes, continue on...
- shr bl,1 ;no, divide the buffer in half
- rcr ax,1 ;by shifting 17 bits
- @@F1:
- mov dx,[MVOurDMAddress]
- out dx,al
- call PCM_pause
- xchg ah,al
- out dx,al
- mov eax,[DMA_Length] ;<------>
- lea eax,[eax*2]
- cmp esi,offset DMA1AddrTable ;is this the 2nd dma controller?
- jz @@lodma03 ;no, use the full length
- shr ax,1
- inc dx ;move to next port address
- @@lodma03:
- dec ax
- inc dx ;move to next port address
- out dx,al
- call PCM_pause
- xchg ah,al
- out dx,al
- ; before we enable the DMA, let's make sure the DRQ is controlled, not floating
- mov al,[edi+mvstate._crosschannel] ;get the state
- mov edx,CROSSCHANNEL
- xor edx,[_MVTranslateCode]
- or al,bCCdrq ;set the DRQ bit to control it
- out dx,al
- mov [edi+mvstate._crosschannel],al ;and save the new state
- ; re-enable the dma now that all programming is done
- mov al,[esi+dmaaddr._dmach] ;get the adjusted dma channel #
- sub dx,dx
- mov dl,[esi+dmaaddr._dmawrsmr]
- out dx,al ;& let'er loose (not moving though...)
- ; all done, return home...
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;
- ; SetupPCMDMAIO -- Setup to output to the DAC
- ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc SetupPCMDMAIO
- push edi
- mov edi,[mvhwShadowPointer]
- ; setup the sample rate timer
-
- mov al,00110110b ;36h Timer 0 & square wave
- mov edx,TMRCTLR
- xor edx,[_MVTranslateCode]
- pushf
- cli
- out dx,al ;setup the mode, etc
- mov [edi+mvstate._tmrctlr],al
- mov ax,[edi+mvstate._samplerate] ;pre-calculated & saved in prior code
- mov edx,SAMPLERATE
- xor edx,[_MVTranslateCode]
- out dx,al ;output the timer value
- call PCM_pause
- xchg ah,al
- out dx,al
- popf
-
- ; Setup the Sample Buffer Counter Timer (T1 & rate generator)
- mov eax,[dword DMA_Length] ;get the count
- add eax,1 ;make it 1 based (1 - 64k)
- mov bl,[init_settings.DMA_no] ;is this a 16 bit channel?
- mov bh,[MVSampleSize] ;CX = sample size, channel
- sub cx,cx ;ch = multiplier, cl=divider
- cmp bx,0003h ;8 bits on 8 bit channel?
- jbe @@mdF1 ;yes, continue on...
- inc cx ;divide by 2
- cmp bx,0007h ;8 bits on 16 bit channel?
- jbe @@mdF1 ;yes, continue on...
- xchg ch,cl ;multiply by 2
- cmp bx,0203h ;16 bits on 8 bit channel?
- jbe @@mdF1 ;yes, continue on...
- sub cx,cx ;no multiply or divide
- @@mdF1:
- dec ax ;<------>
- shr ax,cl ;if 8 on 16 divide by 2
- xchg ch,cl
- shl ax,cl ;if 16 on 8 multiply by 2
- sub cx,cx ;The buffer size is # of bytes, so
- neg bh ;we must convert it to the data size
- adc cx,cx
- shr ax,cl
-
- push edi
- mov edi,[mvhwShadowPointer]
- push edx eax
- mov al,01110100b ;74h Timer 1 & rate generator
- mov edx,TMRCTLR
- xor edx,[_MVTranslateCode]
- cli
- out dx,al
- mov [edi+mvstate._tmrctlr],al ;local timer control register
- pop eax
- mov edx,SAMPLECNT
- xor edx,[_MVTranslateCode]
- mov [edi+mvstate._samplecnt],ax
- out dx,al
- call PCM_pause
- xchg ah,al
- out dx,al
- sti
- xchg ah,al
- pop edx edi
-
- ; Setup the system interrupt mask (IRQ mask)
- mov dx,IRQ1MASKREG
- cmp [init_settings.IRQ_no],8 ;2nd IRQ controller?
- jl @@irqcF2
- mov dl,IRQ2MASKREG
- @@irqcF2:
- in al,dx ;get the mask
- mov ah,[mvTheIRQMask]
- not ah
- and al,ah ;unmask the correct IRQ
- out dx,al ;then let the system know
- ; Setup the Interrupt Control Register
-
- mov edx,INTRCTLRST ;flush any pending interrupts
- xor edx,[_MVTranslateCode] ;xlate the board address
- out dx,al ;of the PCM circuitry
- mov edx,INTRCTLR
- xor edx,[_MVTranslateCode] ;xlate the board address
- in al,dx ;get the real mask
- or al,bICsampbuff ;interrupt on sample buffer count
- out dx,al ;send it..
- mov [edi+mvstate._intrctlr],al ;save it..
- ; enable the 12/16 bit stuff
- test [_MVHWVersionBits],bMV101 ;101 chip?
- jz @@sdhpas1_05 ;no, don't touch this...
- mov cx,((NOT(bSC216bit+bSC212bit)) shl 8) + bSC216bit+bSC212bit
- cmp [mvSampleSize],1 ;12 bit?
- jz @@F3scsi
- mov cx,((NOT(bSC216bit+bSC212bit)) shl 8) + bSC216bit
- cmp [mvSampleSize],2 ;16 bit?
- jz @@F3scsi
- mov cx,((NOT(bSC216bit+bSC212bit)) shl 8) + 0
- @@f3scsi:
- mov edx,SYSCONFIG2
- xor edx,[_MVTranslateCode] ;xlate the board address
- in al,dx
- and al,ch ;clear the bits
- or al,cl ;set the appropriate bits
- out dx,al
- @@sdhpas1_05:
- ; setup the direction, stereo/mono and DMA enable bits
- mov al,bCCmono ;get the stereo/mono mask bit
- and al,0 ;al = bCCmono if in mono mode
- or al,bCCdac ;bit d6 of interrupt control register
- or al,bCCenapcm
- mov edx,CROSSCHANNEL
- xor edx,[_MVTranslateCode] ;xlate the board address
- mov ah,0fh + bCCdrq ;get a mask to load non PCM bits
- and ah,[edi+mvstate._crosschannel] ;grab all but PCM/DRQ/MONO/DIRECTION
- or al,ah ;merge the two states
- xor al,bCCenapcm ;disable the PCM bit
- out dx,al ;send to the hardware
- xor al,bCCenapcm ;enable the PCM bit
- out dx,al ;send to the hardware
- mov [edi+mvstate._crosschannel],al ; and save the new state
- ; Setup the audio filter sample bits
- mov al,[edi+mvstate._audiofilt]
- or al,bFIsrate+bFIsbuff ;enable the sample count/buff counters
- mov edx,AUDIOFILT
- xor edx,[_MVTranslateCode] ;xlate the board address
- out dx,al
- mov [edi+mvstate._audiofilt],al
- sti ; fly baby fly !
- pop edi
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- label PAS16_sample_settings tDAC_ssetings
- tDAC_ssetings <11025,00222,0444,22050>
- tDAC_ssetings <16538,00332,0664,33075>
- tDAC_ssetings <22050,00442,0884,44100>
- tDAC_ssetings <33075,00662,1324,66150>
- tDAC_ssetings <44100,00882,1764,88200>
-
- proc StartPlaying
- mov [MVTypeOfSetup],DMAMASK
- mov [byte DAC_shift_value],6
-
- movzx eax,[byte init_settings.DAC_Samplerate]
- mov ecx,size tDAC_ssetings
- mul ecx
-
- mov ebx,[dword eax+PAS16_sample_settings.DAC_sr]
- mov [dword DAC_sampling_rate],ebx
- mov ebx,[dword eax+PAS16_sample_settings.DAC_mix_buffer_size]
- mov [dword DAC_mix_buffer_size],ebx
- lea ebx,[ebx*4]
- mov [DAC_double_buf2],ebx
- push eax
- mov bl,[init_settings.IRQ_no]
- lea edx,[PAS16_virtualmixxer]
- mov cx,cs
- call setirqvector
- pop eax
- mov [byte MVSampleSize],2
- mov ebx,[dword eax+PAS16_sample_settings.DMA_length]
- lea ebx,[ebx*2]
- mov [dword DMA_length],ebx
- mov eax,[dword eax+PAS16_sample_settings.DMA_real_sr]
- ;@@fff1:
- mov edi,[mvhwShadowPointer]
- mov ecx,eax
- mov eax,1193180
- xor edx,edx
- div ecx
- mov [edi+MVState._samplerate],ax
- ;=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
- ; Program the DMA, then our board circuitry to start the interrupts
- call LoadDMA ;setup the DMA controller
- call SetupPCMDMAIO ;Setup the MV Hardware
- mov [mvStatusWord],1 ;set the global status word
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; Routine from Intel Corp ;
- ; ;
- ; 0=???? ;
- ; 1=???? ;
- ; 2=???? ;
- ; 3=Intel386(TM) processor ;
- ; 4=Intel486(TM) processor ;
- ; 5=Pentium(TM) processor ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- cpu_vendor_id db 12 dup (?)
- cpu_cpu_type db ?
- cpu_c_model db ?
- cpu_stepping db ?
- cpu_id_flag db 0
- cpu_intel_proc db 0
- cpu_feature_flags dw 2 dup (0)
-
- macro @CPUID
- db 0fh
- db 0a2h
- endm
-
- proc get_cpuid
- mov [byte cpu_cpu_type],0
- mov [byte cpu_id_flag],0
- mov [byte cpu_intel_proc],0
- pushad
- mov ebx,esp
- and esp,not 3
- pushf
- pop eax
- mov ecx,eax
- xor eax,40000h
- push eax
- popf
- pushf
- pop eax
- xor eax,ecx
- mov [byte cpu_cpu_type],3
- mov esp,ebx
- jz @@end_get_cpuid
- and esp,not 3
- push ecx
- popf
- mov esp,ebx
- @@check_80486:
- mov [byte cpu_cpu_type],4
- mov eax,ecx
- xor eax,200000h
- push eax
- popf
- pushf
- pop eax
- xor eax,ecx
- je @@end_get_cpuid
- @@check_vendor:
- mov [byte cpu_id_flag],1
- xor eax,eax
- @CPUID
- mov [word cpu_vendor_id],bx
- mov [word 4+cpu_vendor_id],dx
- mov [word 8+cpu_vendor_id],cx
- lea esi,[cpu_vendor_id]
- lea edi,[@@intel_id]
- mov ecx,length @@intel_id
- @@compare:
- repe cmpsb
- or ecx,ecx
- jnz @@end_get_cpuid
- @@intel_processor:
- mov [byte cpu_intel_proc],1
- @@cpuid_data:
- cmp eax,1
- jl @@end_get_cpuid
- xor eax,eax
- inc eax
- @CPUID
- mov [byte cpu_stepping],al
- and [byte cpu_stepping],0fh
- and al,0f0h
- shr al,4
- mov [byte cpu_c_model],al
- and ax,0f00h
- shr ax,8
- mov [byte cpu_cpu_type],al
- mov [word cpu_feature_flags],dx
- @@end_get_cpuid:
- popad
- ret
- @@intel_id:
- db "GenuineIntel"
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- macro @mini_clear_slot
- mov [byte esi],0fch
- mov [byte esi+1],0fh
- mov [byte esi+2],0
- endm
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc find_pats_seqs
- mov [byte funk_info.no_of_sequences],0
- mov edi,offset funk_hr ; find no of patterns
- xor al,al
- mov ecx,256
- @@find_patseq:
- cmp [byte edi+tfunk_hr.order_list],0FFh
- je @@end_patseq
- inc [byte funk_info.no_of_sequences]
- cmp [byte edi+tfunk_hr.order_list],al
- jbe @@test_next
- mov al,[byte edi+tfunk_hr.order_list]
- @@test_next:
- inc edi
- dec ecx
- jnz @@find_patseq
- @@end_patseq:
- dec [byte funk_info.no_of_sequences]
- inc al
- mov [byte funk_info.no_of_patterns],al
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc resync_sample_ptrs
- mov al,[byte init_settings.card_type]
- cmp al,SB_CARD
- je @@DAC_CARD
- cmp al,SBPRO_CARD
- je @@DAC_CARD
- cmp al,GUS_VARB_CARD
- je @@DSP_CARD
- cmp al,SB15EM_CARD
- je @@DAC_CARD
- cmp al,SB16_CARD
- je @@DAC_CARD
- cmp al,GUS_FIXB_CARD
- je @@DSP_CARD
- cmp al,PAS16_CARD
- je @@DAC_CARD
- ret
- @@DAC_CARD:
- mov eax,[dword funk_sd_ptr]
- mov [dword funk_info.sample_ptrs],eax
- jmp @@calc
- @@DSP_CARD:
- mov [dword funk_info.sample_ptrs],32
- @@calc:
- lea ebx,[funk_sb]
- xor edi,edi
- mov cl,3fh
- @@sync_sp:
- mov eax,[dword ebx+tfunk_sb.length]
- add eax,[dword edi+funk_info.sample_ptrs]
- add ebx,size tfunk_sb
- add edi,4
- mov [dword edi+funk_info.sample_ptrs],eax
- dec cl
- jnz @@sync_sp
- mov eax,[dword ebx+tfunk_sb.length]
- add eax,[dword edi+funk_info.sample_ptrs]
- mov [dword sample_block_size],eax
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc init_for_play
- mov [byte sequence_ofs_old],0ffh
- mov [byte pattern_ofs2_old],0ffh
- mov [byte funk_info.sequence_ofs],0
- mov [byte funk_info.pattern_ofs],0
- mov [byte funk_info.tempo],04h
- mov [byte funk_info.tempo_count],0
- mov [byte funk_info.master_volume],0fh
- mov [byte funk_info.trek_status],STOP
- call find_pats_seqs
- lea edi,[funk_chan1]
- mov cl,8
- @@clear_funk_chan:
- ;─control system─────────────────
- mov [byte edi+tfunk_chan.command],0fh
- mov [byte edi+tfunk_chan.com_val],0
- mov [byte edi+tfunk_chan.comspd_count],0
- mov [byte edi+tfunk_chan.sample],3fh
- mov [dword edi+tfunk_chan.start],0ffffffffh
- mov [dword edi+tfunk_chan.length],100000h
- mov [byte edi+tfunk_chan.funkctrl],0
- mov [byte edi+tfunk_chan.port_type],0
- mov [byte edi+tfunk_chan.sample_ofs_parm],08h
- mov [byte edi+tfunk_chan.vib_waveform],0
- mov [byte edi+tfunk_chan.vol_vib_waveform],0
- mov [byte edi+tfunk_chan.balance],80h
- mov [byte edi+tfunk_chan.retrig_limit],4
- mov [byte edi+tfunk_chan.arp_speed],3
- ;─note system────────────────────
- mov [byte edi+tfunk_chan.note_command],0fh
- mov [byte edi+tfunk_chan.note_com_val],0
- mov [byte edi+tfunk_chan.note_comspd_count],0
- mov [byte edi+tfunk_chan.note],03fh
- mov [word edi+tfunk_chan.ifreq],0
- mov [word edi+tfunk_chan.ifreq_vibrato],0
- mov [word edi+tfunk_chan.ifreq_portdest],0
- mov [dword edi+tfunk_chan.rfreq],0
- mov [dword edi+tfunk_chan.rfreq_adjust],0
- mov [dword edi+tfunk_chan.rfreq_portdest],0
- mov [byte edi+tfunk_chan.vib_ptr],0
- mov [byte edi+tfunk_chan.note_beat_count],0
- ;─volume system──────────────────
- mov [byte edi+tfunk_chan.volume_command],0fh
- mov [byte edi+tfunk_chan.volume_com_val],0
- mov [byte edi+tfunk_chan.volume_comspd_count],0
- mov [byte edi+tfunk_chan.volume],0
- mov [byte edi+tfunk_chan.volume_vibrato],0
- mov [byte edi+tfunk_chan.volume_portdest],0
- mov [byte edi+tfunk_chan.rvolume],0
- mov [byte edi+tfunk_chan.vol_vib_ptr],0
- mov [byte edi+tfunk_chan.volume_beat_count],0
-
- mov [dword edi+tfunk_chan.CARD_sample_ptr],0
- mov [dword edi+tfunk_chan.CARD_freq],100
- mov [dword edi+tfunk_chan.CARD_freq_attract],0
- mov [dword edi+tfunk_chan.CARD_volume],0
- add edi,size tfunk_chan
- dec cl
- jnz @@clear_funk_chan
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; 'info' code: ;
- ; ;
- ; 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 2 2 2 2 2 2 2 2 3 3 3 3 3 3 3 3 ;
- ; \-day---/ \month--/ \----year---/ \-card/ \-CPU-/ | 0 0 0 0 0 0 0 ;
- ; | \memory reqi/ ;
- ; | ;
- ; 16 bit = 1 ----| ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc clear_all_funk
- ;CLEAR HEADER
- mov [dword funk_hr.sig],"knuF"
- mov ah,2ah
- int 21h
- movzx eax,dl
- movzx edx,dh
- shl edx,5
- or eax,edx
- sub ecx,1980
- shl ecx,9
- or eax,ecx
- mov [word funk_hr.info],ax
- movzx ax,[byte init_settings.card_type]
- mov bl,[byte cpu_cpu_type]
- shl bl,4
- or al,bl
- mov [word 2+funk_hr.info],ax
- mov [byte funk_hr.loop_order],0ffh
- lea edi,[funk_hr.order_list]
- mov al,0ffh
- mov ecx,256
- rep stosb
- mov al,03fh
- mov ecx,128
- rep stosb
- ;CLEAR SAMPLE BLOCK
- mov dl,64
- lea edi,[funk_sb]
- @@clear_sb:
- xor al,al
- mov ecx,19
- rep stosb
- sub edi,19
- mov [dword edi+tfunk_sb.start],0ffffffffh
- mov [dword edi+tfunk_sb.length],0
- mov [byte edi+tfunk_sb.volume],0ffh
- mov [byte edi+tfunk_sb.balance],80h
- mov [byte edi+tfunk_sb.pt_and_sop],08h
- mov [byte edi+tfunk_sb.vv_waveform],0
- mov [byte edi+tfunk_sb.rl_and_as],43h
- add edi,size tfunk_sb
- dec dl
- jnz @@clear_sb
- ;CLEAR PATTERNS
- mov esi,[dword funk_pd_ptr]
- mov ecx,8*64*128
- @@clear_patterns:
- @mini_clear_slot
- add esi,3
- dec ecx
- jnz @@clear_patterns
- call resync_sample_ptrs
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc upload_exteral_data
- cmp [byte init_settings.card_type],GUS_VARB_CARD
- je @@GUS_mem_move
- cmp [byte init_settings.card_type],GUS_FIXB_CARD
- je @@GUS_mem_move
- ret
- @@GUS_mem_move:
- call GUS_reset
- mov esi,[dword funk_sd_ptr]
- mov edi,[dword funk_info.sample_ptrs]
- mov ecx,[dword sample_block_size]
- sub ecx,[dword funk_info.sample_ptrs]
- call GUS_upload
- call GUS_reset
- call GUS_intready
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; returns eax, esi ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc find_funk_size_parity
- mov ebx,[dword file_handle_funk]
- mov eax,4202h
- xor edx,edx
- int 21h
- push eax
- mov eax,4200h
- mov edx,size tfunk_hr
- int 21h
- xor esi,esi
- @@sum_file:
- mov edx,[_0b8000h]
- add edx,8000
- mov ecx,8000
- mov ah,3fh
- int 21h
- or eax,eax
- jz @@done_sum
- @@count:
- movzx ecx,[byte edx]
- add esi,ecx
- inc edx
- dec eax
- jnz @@count
- jmp @@sum_file
- @@done_sum:
- mov ebx,[dword file_handle_funk]
- mov eax,4200h
- xor edx,edx
- int 21h
- pop eax
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; edx = points to the filename ANSIIZ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc load_funk_module
- push edx
- call clear_all_funk
- mov eax,3d00h
- pop edx
- int 21h
- jc @@mess1
- mov [dword file_handle_funk],eax
- call find_funk_size_parity ; find parity and size
- mov [dword @@temp_size],eax
- mov [dword @@temp_parity],esi
- mov ebx,[dword file_handle_funk]
- mov edx,offset funk_hr
- mov ecx,(size tfunk_hr)+((size tfunk_sb)*64)
- mov ah,3fh ; read header+sample block
- int 21h
- cmp [dword funk_hr.sig],"knuF"
- jne @@mess2
- movzx eax,[byte 3+funk_hr.info] ; find memory requirement
- and al,11111110b
- add al,2
- shl eax,18
- cmp eax,[dword sample_memory_lim]
- ja @@mess3
- call find_pats_seqs
- call resync_sample_ptrs
- mov eax,[dword @@temp_size] ; check size and parity
- cmp [dword funk_hr.LZH_check_size],eax
- jne @@mess2
- mov eax,[dword @@temp_parity]
- mov [dword funk_hr.LZH_check_sum],eax
- mov eax,600h ; save patterns
- movzx ecx,[byte funk_info.no_of_patterns]
- mul ecx
- mov ebx,[dword file_handle_funk]
- mov edx,[dword funk_pd_ptr]
- mov ecx,eax
- mov ah,3fh
- int 21h
- mov eax,[dword sample_block_size]
- sub eax,[dword funk_info.sample_ptrs]
- mov ebx,[dword file_handle_funk]
- mov edx,[dword funk_sd_ptr]
- mov ecx,eax
- mov ah,3fh
- int 21h
- mov ebx,[dword file_handle_funk]
- mov ah,3eh ; close
- int 21h
- call upload_exteral_data
- mov al,0
- ret
- @@mess1:
- mov al,1 ;can't load song
- ret
- @@mess2:
- call clear_all_funk ;invalid song
- mov al,2
- @@mess3:
- call clear_all_funk ;not enough sample mem
- mov al,3
- ret
- @@temp_size:
- dd ?
- @@temp_parity:
- dd ?
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc dnload_exteral_data
- cmp [byte init_settings.card_type],GUS_VARB_CARD
- je @@GUS_mem_move
- cmp [byte init_settings.card_type],GUS_FIXB_CARD
- je @@GUS_mem_move
- ret
- @@GUS_mem_move:
- call GUS_reset
- mov edi,[dword funk_sd_ptr]
- mov esi,[dword funk_info.sample_ptrs]
- mov ecx,[dword sample_block_size]
- sub ecx,[dword funk_info.sample_ptrs]
- call GUS_dnload
- call GUS_reset
- call GUS_intready
- ret
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ; edx = points to the filename ANSIIZ ;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc save_funk_module
- mov [dword @@fn],edx
- call find_pats_seqs
- call resync_sample_ptrs
- cmp [byte funk_info.no_of_sequences],0ffh
- je @@mess1
- mov eax,[dword sample_block_size]
- cmp eax,[dword funk_info.sample_ptrs]
- je @@mess2
- ; disk space test
- mov ah,36h
- xor dl,dl
- int 21h
- mul ecx
- mul ebx
- or edx,edx
- jnz @@heaps_of_space
- push eax
- mov eax,600h
- movzx ecx,[byte funk_info.no_of_sequences]
- inc ecx
- mul ecx
- mov ecx,[dword sample_block_size]
- sub ecx,[dword funk_info.sample_ptrs]
- add eax,ecx
- add eax,2048+500
- pop ecx
- cmp eax,ecx
- jbe @@heaps_of_space
- jmp @@mess4
- @@heaps_of_space:
- call dnload_exteral_data
- mov eax,3c00h
- mov edx,[dword @@fn]
- xor ecx,ecx
- int 21h
- jc @@mess3
- mov [dword file_handle_funk],eax
- mov ebx,eax
- mov edx,offset funk_hr
- mov ecx,(size tfunk_hr)+((size tfunk_sb)*64)
- mov ah,40h ; save tables+sample block
- int 21h
- mov eax,600h ; save patterns
- movzx ecx,[byte funk_info.no_of_patterns]
- mul ecx
- mov ebx,[dword file_handle_funk]
- mov edx,[dword funk_pd_ptr]
- mov ecx,eax
- mov ah,40h
- int 21h
- mov eax,[dword sample_block_size]
- sub eax,[dword funk_info.sample_ptrs]
- mov ebx,[dword file_handle_funk]
- mov edx,[dword funk_sd_ptr]
- mov ecx,eax
- mov ah,40h
- int 21h
- ; write memory requirement
- mov eax,[dword sample_block_size]
- sub eax,[dword funk_info.sample_ptrs]
- and al,11111110b
- shr eax,18
- ;; or al,10000000b
- ;; set bit 7 if a 16 bit sample
- mov [byte 3+funk_hr.info],al
- call find_funk_size_parity
- mov [dword funk_hr.LZH_check_size],eax
- mov [dword funk_hr.LZH_check_sum],esi
- lea edx,[funk_hr]
- mov ecx,size tfunk_hr
- mov ah,40h
- int 21h
- mov ah,3eh ;close
- int 21h
- mov al,0
- ret
- @@mess1:
- mov al,0 ;can't save song with emptylist
- ret
- @@mess2:
- mov al,1 ;no samples
- ret
- @@mess3:
- mov al,2 ;can't save song
- ret
- @@mess4:
- mov al,3 ;not enough save on harddisk
- ret
- @@fn dd ?
- endp
-
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- ; ;
- ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
- proc scard_env
- call GUS_env
- jc @@SB
- ret
- @@SB:
- call SB_env
- jc @@no_card
- ret
- @@no_card:
- mov [byte init_settings.card_type],0ffh
- ret
- endp
-
- proc scard_detect
- call init_for_play
- call AllocDMAregion ;init DMA variables
- jc @@memory_error ;and other memory
- add [dword DAC_mix_buffer],edx
- add [dword DAC_mix_buffer_right],edx
- add [dword DAC_mix_buffer2],edx
- add [dword DAC_PHYSICAL_PAGE],ebx
- mov edx,funk_pd_size
- call Allocate_Memory
- jc @@memory_error
- mov [dword funk_pd_ptr],edx
- mov edx,[dword sample_memory_lim]
- call Allocate_Memory
- jc @@memory_error
- mov [dword funk_sd_ptr],edx
-
- cmp [byte init_settings.card_type],SB_CARD
- je @@sb_family
- cmp [byte init_settings.card_type],SBPRO_CARD
- je @@sb_family
- cmp [byte init_settings.card_type],GUS_VARB_CARD
- je @@gus
- cmp [byte init_settings.card_type],SB15EM_CARD
- je @@sb_family
- cmp [byte init_settings.card_type],SB16_CARD
- je @@sb_family
- cmp [byte init_settings.card_type],GUS_FIXB_CARD
- je @@gus
- cmp [byte init_settings.card_type],PAS16_CARD
- je @@pas_family
- @@memory_error:
- ret
- @@sb_family:
- call SB_detect
- ret
- @@gus:
- call GUS_detect
- ret
- @@pas_family:
- xor edi,edi
- call mvGetHWVersion
- pushf
- call MVInitStatePtr
- popf
- ret
- endp
-
- proc scard_init
- mov edi,[dword DAC_mix_buffer] ; clear buffers
- mov ecx,1000h/2
- mov eax,8000h
- rep stosw
- mov edi,[dword DAC_mix_buffer_right] ; clear buffers
- mov ecx,1000h/2
- mov eax,8000h
- rep stosw
- mov ecx,2000h
- mov edi,[dword DAC_mix_buffer2]
- mov al,80h
- rep stosb
- cmp [byte init_settings.card_type],SB_CARD
- je @@sb08
- cmp [byte init_settings.card_type],SBPRO_CARD
- je @@sb08
- cmp [byte init_settings.card_type],GUS_VARB_CARD
- je @@gus
- cmp [byte init_settings.card_type],SB15EM_CARD
- je @@sb08
- cmp [byte init_settings.card_type],SB16_CARD
- je @@sb16
- cmp [byte init_settings.card_type],GUS_FIXB_CARD
- je @@gus
- cmp [byte init_settings.card_type],PAS16_CARD
- je @@pas_family
- ret
- @@sb08:
- call SB08_init
- jc @@sb08_e
- call SB08_deinit
- call SB08_init
- @@sb08_e:
- ret
- @@sb16:
- mov ecx,2000h/2
- mov edi,[dword DAC_mix_buffer2]
- xor eax,eax
- rep stosw
- call SB16_init
- ret
- @@gus:
- call GUS_init
- ret
- @@pas_family:
- mov ecx,2000h/2
- mov edi,[dword DAC_mix_buffer2]
- xor eax,eax
- rep stosw
- call InitPCM
- call StartPlaying
- ret
- endp
-
- proc scard_deinit
- cmp [byte init_settings.card_type],SB_CARD
- je @@sb08
- cmp [byte init_settings.card_type],SBPRO_CARD
- je @@sb08
- cmp [byte init_settings.card_type],GUS_VARB_CARD
- je @@gus
- cmp [byte init_settings.card_type],SB15EM_CARD
- je @@sb08
- cmp [byte init_settings.card_type],SB16_CARD
- je @@sb16
- cmp [byte init_settings.card_type],GUS_FIXB_CARD
- je @@gus
- cmp [byte init_settings.card_type],PAS16_CARD
- je @@pas_family
- ret
- @@sb08:
- call SB08_deinit
- ret
- @@sb16:
- call SB16_deinit
- ret
- @@gus:
- call GUS_deinit
- ret
- @@pas_family:
- call StopPCM
- ret
- endp
-