Subversion Repositories Kolibri OS

Rev

Rev 109 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
31 halyavin 1
;---------------------------------------------------------------------
2
;
3
;   MenuetOS AC97 WAV Player
4
;
5
;    0.03  November 10, 2004  doesn't halt if file not found
6
;    0.04  November 11, 2004  better positioning (with mouse)
7
;    0.05  November 14, 2004  internals clean up
8
;                             fixed cutting sound at the edges
9
;    0.06  November 17, 2004  fixed many bugs
10
;    0.07  Nov      20, 2004  deactivates text box when 'play' pressed
11
;                             stops playing before closing a window
12
;    0.08  Nov      24, 2004  added support for 8bit and mono modes
13
;                             +variable rate for some chipsets
139 diamond 14
;    0.09  August   26, 2006  modified to use function 70
31 halyavin 15
;
139 diamond 16
;   Use [flat assembler 1.64] to compile.
31 halyavin 17
;
18
;---------------------------------------------------------------------
19
 
20
  use32 	 ; turn on 32 bit mode
21
  org	  0x0	      ; the program is placed at 0 offset
22
 
23
  db	 'MENUET01'	; 8-byte identifier of MenuetOS application
24
  dd	 0x01	      ; header version (always 1)
25
  dd	 START	       ; address of the beginning of the code
26
  dd	 IMAGE_END     ; size of the program's image
27
  dd	 MEMORY_END	; how much memory does it need
28
  dd	 STACK_P     ; a pointer to the top of the stack
29
  dd	 textbox_string
30
;  dd     0x0             ; address of buffer for parameters (not used)
31
  dd	 0x0	     ; reserved
32
 
33
;---------------------------------------------------------------------
34
 
35
include "macros.inc"	 ; standart macros & constants
36
include "meosfunc.inc"	   ; MenuetOS API functions names
37
include "debug.inc"	; printing to debug board
38
include "constant.inc"	   ; BIT?? constants
39
include "ac97.inc"     ; AC'97 constants
40
include "pci.inc"     ; PCI interface
41
include "codec.inc"	; functions for configuring codec
42
include "frontend.inc"	   ; main window
43
 
44
;---------------------------------------------------------------------
45
 
46
;  Uncomment these strings if you don't want to receive debug messages:
47
 
48
;  macro dps str   {}    ; dps prints a string without CRLF
49
;  macro dpd num   {}    ; prints unsigned decimal number
50
;  macro pregs     {}    ; outputs EAX, EBX, ECX, EDX
51
;  macro newline   {}    ; CRLF
52
;  macro print str {}    ; output a string with CRLF
53
;  macro dph arg   {}    ; print hex number
54
 
55
;---------------------------------------------------------------------
56
 
57
;macro device id, addr { dd id, addr }
58
macro devices [id, str]
59
{
60
  common
61
    label supported_devices dword
62
  forward
63
    local string
64
    dd id
65
    dd string
66
  forward
67
    string db str
68
    db 0
69
}
70
 
71
 
72
devices \
73
  (ICH_DID shl 16) + INTEL_VID,      "ICH"    ,\
74
  (ICH0_DID shl 16) + INTEL_VID,     "ICH0"   ,\
75
  (ICH2_DID shl 16) + INTEL_VID,     "ICH2"   ,\
76
  (ICH3_DID shl 16) + INTEL_VID,     "ICH2"   ,\
77
  (ICH4_DID shl 16) + INTEL_VID,     "ICH4"   ,\
78
  (ICH5_DID shl 16) + INTEL_VID,     "ICH5"   ,\
79
  (MX440_DID shl 16) + INTEL_VID,    "440MX"  ,\
80
  (SI7012_DID shl 16) + SIS_VID,     "SI7012" ,\
81
  (NFORCE_DID shl 16) + NVIDIA_VID,  "NForce" ,\
82
  (NFORCE2_DID shl 16) + NVIDIA_VID, "NForce2",\
83
  (AMD8111_DID shl 16) + AMD_VID,    "AMD8111",\
84
  (AMD768_DID shl 16) + AMD_VID,     "AMD768"
85
dd    0
86
 
87
 
88
;---------------------------------------------------------------------
89
;---  MAIN PROGRAM  --------------------------------------------------
90
;---------------------------------------------------------------------
91
 
92
START:
93
 
94
; Print PCI version (for example, 2.16)
95
;        mcall   MF_PCI, 0
96
;        mov     bl, al
97
;        movzx   eax, ah
98
;        dps    "PCI version: "
99
;        dpd     eax
100
;        movzx   eax, bl
101
;        dpd     eax
102
;        newline
103
 
104
; Check PCI access mechanism (must be 1 or 2)
105
    mcall    MF_PCI, 2
106
    dec    al
107
    cmp    al, 1
108
    jna    @f
109
    print    "Error: cannot access PCI bus."
110
    jmp    exit
111
;        dps     "PCI returned "
112
;        movzx   eax, al
113
;        dpd     eax
114
;        newline
115
     @@:
116
 
117
 
118
; Get last bus & then check all buses & devices
119
    mcall    MF_PCI, 1
120
    mov    [lastbus], al
121
 
122
     ; looking for a compatible device
123
    mov    [bus], -1
124
  .next_bus:
125
    inc    [bus]
126
 
127
    mov    al, [lastbus]
128
    cmp    al, [bus]
129
    jb	  .device_not_found
130
 
131
    mov    [devfn], 0
132
  .next_devfn:
133
 
134
    mov    cl, 0
135
    call    pciRegRead32
136
 
137
    mov    edi, supported_devices
138
      @@:
139
    mov    ebx, [edi]
140
    test    ebx, ebx
141
    jz	  @f
142
    cmp    eax, ebx
143
    jnz    .skip
144
    add    edi, 4
145
    mov    [device_id], eax
146
    mov    edx, [edi]
147
    call    debug_outstr
148
    jmp    proceed
149
       .skip:
150
    add    edi, 8
151
    jmp    @b
152
      @@:
153
 
154
    inc    [devfn]
155
    cmp    [devfn], 255
156
    jb	  .next_devfn
157
 
158
    jmp    .next_bus
159
 
160
 
161
  .device_not_found:
162
    print    "Could not find Intel AC'97 compatible codec!"
163
    print    "1) Check if it's enabled in BIOS."
164
    print    "2) Check if your device is included in the device list."
165
    jmp    exit
166
 
167
 
168
 proceed:
169
    print    " integrated AC97 audio codec detected."
170
    mov    eax, [device_id]
171
    cmp    eax, (ICH4_DID shl 16) + INTEL_VID
172
    je	  .newich
173
    cmp    eax, (ICH5_DID shl 16) + INTEL_VID
174
    jne    .nonewich
175
      .newich:
176
    mov    [AC97ICH4], 1
177
      .nonewich:
178
 
179
    cmp    eax, (SI7012_DID shl 16) + SIS_VID
180
    jne    @f
181
    mov    [SI7012], 1
182
      @@:
183
 
184
;---------------------------------------------------------------------
185
 
186
; Get NAMBAR register base port address & save it
187
    mov    cl, NAMBAR_REG
188
    call    pciRegRead16
189
 
190
    and    eax, 0xFFFE
191
    mov    [NAMBAR], ax
192
    test    eax, eax
193
    jnz    .mixer_base_ok
194
 
195
    print    "Error: Intel ICH based AC97 audio codec disabled in BIOS!"
196
    jmp    exit
197
 
198
 .mixer_base_ok:
199
    dps    "NAMBAR: "
200
    dph    eax
201
 
202
; Get NABMBAR & save it
203
    mov    cl, NABMBAR_REG
204
    call    pciRegRead16
205
    and    eax, 0xFFC0
206
    mov    [NABMBAR], ax
207
    test    eax, eax
208
    jnz    .bm_base_ok
209
 
210
    print    "Error: Intel ICH based AC97 audio codec disabled in BIOS!"
211
    jmp    exit
212
 
213
 .bm_base_ok:
214
    dps    " NABMBAR: "
215
    dph    eax
216
    newline
217
 
218
;---------------------------------------------------------------------
219
 
220
; Get IRQ (not used)
221
    mov    cl, IRQ_REG
222
    call    pciRegRead8
223
    mov    [AC97IRQ], al
224
 
225
; Get Interrupt pin (not used)
226
    mov    cl, INT_REG
227
    call    pciRegRead8
228
    mov    [AC97INT], al
229
 
230
; AC97ICH4 should work then...
231
    cmp    [AC97ICH4], 1
232
    jne    .skip_ich4_init
233
 
234
    mov    cl, ICH4_CFG_REG  ; 0x41
235
    call    pciRegRead8
236
    or	  al, 0x1
237
    mov    dl, al
238
    call    pciRegWrite8
239
 
240
    mov    cl, 0x54
241
    call    pciRegRead16
242
    and    eax, 0xFFFF
243
    dps    "Power Control & Status: "
244
    dph    eax
245
    newline
246
 .skip_ich4_init:
247
 
248
;---------------------------------------------------------------------
249
 
250
    mov    cl, PCI_CMD_REG
251
    call    pciRegRead16	   ; read PCI command register
252
    mov    dx, ax
253
    or	  dx, IO_ENA+BM_ENA+BIT10    ; enable IO and bus master + disable
254
		       ;  interrupts
255
    call    pciRegWrite16
256
 
257
;---------------------------------------------------------------------
258
 
259
    print    "Enabling access to ports..."
260
 
261
    movzx    ecx, [NAMBAR]
262
    mov    edx, ecx
263
    add    edx, NAM_SIZE
264
    mcall    MF_PORTS, PRT_RESERVE
265
    test    eax, eax
266
    jz	  @f
267
    print    "Error: couldn't enable access to ports"
268
    jmp    exit
269
     @@:
270
 
271
    movzx    ecx, [NABMBAR]
272
    mov    edx, ecx
273
    add    edx, NABM_SIZE
274
    mcall    MF_PORTS, PRT_RESERVE
275
    test    eax, eax
276
    jz	  @f
277
    print    "Error: couldn't enable access to ports"
278
    jmp    exit
279
     @@:
280
 
281
;---------------------------------------------------------------------
282
 
283
; setup the Codec
284
    mov    eax, 48000
285
    call    codecConfig 	 ; unmute codec, set rates.
286
    test    eax, eax
287
    jnz    @f
288
    print    "Error: cannot initialize AC97 device."
289
    jmp    fpexit
290
       @@:
291
 
292
    print    "Congrutalations! Your device has been initialized properly!"
293
    call    print_info
294
 
295
;---------------------------------------------------------------------
296
 
297
; register reset the DMA engine.
298
    mov    edx, PO_CR_REG    ; PCM out control register
299
    mov    al, RR	 ; reset
300
    call    NABMBAR_write_byte
301
 
302
;start fix for MM (1)
303
    mcall  MF_INTERNAL_SERVICES,ALLOC_PHYS_MEM,120*1024
304
    test   eax,eax
305
    jz     no_phys_buffers             ;not enough memory
306
    mov    [phys_wav_buffer1],eax
307
    add    eax,60*1024
308
    mov    [phys_wav_buffer2],eax
309
    mcall  MF_INTERNAL_SERVICES,ALLOC_PHYS_MEM,32*8
310
    test   eax,eax
311
    jnz    @f
312
    mcall  MF_INTERNAL_SERVICES,FREE_PHYS_MEM,[phys_wav_buffer1]
313
    jmp    no_phys_buffers
314
@@:
315
    mov    [phys_bdl_buffer],eax
316
;end fix for MM (1)
317
 
318
; create Buffer Descriptors List
319
    call    prepare_BDL
320
 
321
; open player's window
322
    mcall    MF_THREAD, THR_CREATE, thread, thread_stack
323
 
324
; wait for command
325
  .new_check:
326
    cmp    [status], ST_PLAY
327
    jne    @f
328
    call    play
329
      @@:
330
    cmp    [status], ST_STOP
331
    jne    @f
332
    call    stop
333
      @@:
334
    cmp    [status], ST_EXIT
335
    je	  stopexit
336
 
337
    mcall    MF_DELAY, 10
338
    jmp    .new_check
339
 
340
stopexit:
341
    call    stop
342
 
343
fpexit:
344
 
345
; free ports
346
    movzx    ecx, [NAMBAR]
347
    mov    edx, ecx
348
    add    edx, NAM_SIZE
349
    mcall    MF_PORTS, PRT_FREE
350
 
351
    movzx    ecx, [NABMBAR]
352
    mov    edx, ecx
353
    add    edx, NABM_SIZE
354
    mcall    MF_PORTS, PRT_FREE
355
 
356
;---------------------------------------------------------------------
357
;start fix for MM (2)
358
    mcall  MF_INTERNAL_SERVICES,FREE_PHYS_MEM,[phys_bdl_buffer]
359
    mcall  MF_INTERNAL_SERVICES,FREE_PHYS_MEM,[phys_wav_buffer1]
360
;end fix for MM (2)
361
exit:
362
    mcall    MF_EXIT
363
no_phys_buffers:
364
    print  "allocation of physical buffers failed"
365
    jmp    exit
366
 
367
;---------------------------------------------------------------------
368
;---  FUNCTIONS  -----------------------------------------------------
369
;---------------------------------------------------------------------
370
 
371
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
372
;; prepare_BDL - initializes BUFFER DESCRIPTORS LIST
373
prepare_BDL:
374
    mov    ecx, 32 / 2	  ; make 32 entries in BDL
375
    mov    edi, BDL_BUFFER
376
;    call   get_my_address
377
    mov    ebx, 30*1024
378
    cmp    [SI7012], 1
379
    jne    @f
380
    add    ebx, ebx
381
@@:
382
    ; set buf. desc. 0 to start of data file in memory
383
    push   eax
384
;    add    eax, WAV_BUFFER1
385
;start fix for MM (6)
386
    mov    eax,[phys_wav_buffer1]
387
;end fix for MM (6)
388
    stosd
389
    ; set length to 60k samples. 1 sample is 16 bit or 2 bytes.
390
    mov    eax, ebx ;60*1024   ; number of samples
391
    or	   eax, BUP
392
    stosd
393
 
394
    mov    eax, [esp]
395
;    add    eax, WAV_BUFFER2
396
;start fix for MM (7)
397
    mov    eax,[phys_wav_buffer2]
398
;end fix for MM (7)
399
    stosd
400
    mov    eax, ebx ;60*1024
401
    or	   eax, BUP
402
    stosd
403
 
404
    pop    eax
405
    loop   @b
406
 
407
 
408
    ; tell the DMA engine where to find our list of Buffer Descriptors.
409
    ; eax = base addr!
410
;start fix for MM (3)
411
  ;copy to physical memory
412
    mcall  MF_INTERNAL_SERVICES,SET_PHYS_BUFFER,[phys_bdl_buffer],BDL_BUFFER,32*8
413
  ;physical address of bdl
414
    mov    eax,[phys_bdl_buffer]
415
;end fix for MM (3)
416
    mov    edx, PO_BDBAR_REG
417
;    add    eax, BDL_BUFFER
418
    call   NABMBAR_write_dword
419
 
420
ret
421
 
422
 
423
;---------------------------------------------------------------------
424
 
425
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
426
;; stop - stops current music
427
;; in:  nothing
428
;; out: nothing
429
stop:
430
;        print   "STOP!"
431
    push    eax edx
432
 
433
    mcall    MF_DELAY, 10
434
    mov    edx, PO_CR_REG
435
    mov    al, 0
436
    call    NABMBAR_write_byte
437
    cmp    [status], ST_STOP
438
    jne    .exit
439
    mov    [status], ST_DONE
440
      .exit:
441
 
442
    pop    edx eax
443
ret
444
 
445
;---------------------------------------------------------------------
446
 
447
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
448
;; play - plays wav file!
449
;; in:  nothing
450
;; out: nothing (but sound :)   !corrupts registers!
451
play:
139 diamond 452
    ; at first, reset file and get file size
453
        mcall   MF_SYSTREE, attrinfo
454
        test    eax, eax
455
        jnz     .notfound
456
        mov     eax, [fileattr+32]
457
        mov     [file_size], eax
458
    mov    [fileinfo.first_byte], 0
31 halyavin 459
    mcall    MF_SYSTREE, fileinfo ; load a block, returns error code in eax
460
		     ;   and size of the file in ebx
461
    test    eax, eax	     ; 0 - successful
462
    jz	  @f
139 diamond 463
        cmp     eax, 6          ; 6 = eof - successful too
464
        jz      @f
465
.notfound:
31 halyavin 466
    print    "AC97: File not found!"
467
    mov    [status], ST_STOP
468
    jmp    .exit
469
     @@:
470
 
471
    mov    al, [LOAD_BUFFER+32] ; bytes per sample
472
    dec    al
473
    jz	  @f
474
    cmp    al, 3
475
    je	  @f
476
    sub    al, [LOAD_BUFFER+22] ; channels
477
    add    al, 2
478
      @@:
479
    mov    [wav_mode], al
480
 
481
    pusha
482
    movzx    ebx,word [LOAD_BUFFER+24]
483
    mov   eax,48000
484
    xor   edx,edx
485
    div   ebx
486
    mov   [difference_of_frequency],al
487
;        dph   eax
488
    mov   ecx,edx
489
    imul  eax,ecx,10
490
    xor   edx,edx
491
    div   ebx
492
    mov   ecx,edx
493
    imul  ecx,10
494
    push  eax
495
    mov   eax,ecx
496
    xor   edx,edx
497
    div   ebx
498
;        dph   eax
499
    cmp   eax,5
500
    jl	  .temp_15
501
    pop   eax
502
;        dph   eax
503
 
504
    inc   eax
505
    jmp   .temp_16
506
     .temp_15:
507
    pop   eax
508
     .temp_16:
509
    mov   [difference_of_frequency_1],al
510
;        dph   eax
511
    xor   edx,edx
512
    movzx  ebx,[difference_of_frequency]
513
    imul   ebx,10
514
    add    bl,[difference_of_frequency_1]
515
    mov   [difference_of_frequency_2],bl
516
;        dph   ebx
517
    popa
518
 
519
    movzx    eax, word [LOAD_BUFFER+24]
520
    ;dps "Freq: "
521
    ;dpd eax
522
    ;newline
523
    call    set_sample_rate
524
 
525
 
526
    ; change the last_valid_index to the (current_index-1)
527
    ; the LVI register tells the DMA engine where to stop playing
528
    call    updateLVI
529
 
530
    ; if current index is odd, load buffer 1 then 0, jump to tuneLoop
531
    ; if it is even, buffers 0 then 1; tuneLoop1
532
    call    getCurrentIndex
533
    and    eax, BIT0
534
 
535
    mov    esi, eax
536
    push    eax
537
    call    update_next_buffer
538
    pop    eax
539
    xor    eax, 1
540
    call    update_next_buffer
541
 
542
    ; start playing!
543
    mov    edx, PO_CR_REG
544
    mov    al, RPBM
545
    call    NABMBAR_write_byte
546
 
547
    jmp    [jumpto+esi*4]
548
 
549
 
550
   .tuneLoop:
551
    ; wait while the current_index is even
552
    @@:
553
;        dps     "a"
554
    mcall    MF_DELAY, 7
555
    call    getCurrentIndex
556
    test    al, BIT0
557
    jz	  @b	   ; loop if not ready yet
558
;        print   "fa"
559
 
560
    call    updateLVI
561
 
562
    mov    eax, 0
563
    call    update_next_buffer
564
    test    al, al
565
    jnz    .exit_wait
566
 
567
    cmp    [status], ST_PLAY
568
    jne    .exit
569
 
570
    test    [volume], 0x10000000 ; test volume_changed bit
571
    je	  @f
572
    mov    al, byte [volume]
573
    call    setVolume
574
    and    [volume], 0x0FFFFFFF ; clear vloume_changed bit
575
     @@:
576
 
577
     .tuneLoop1:
578
     @@:
579
;        dps     "b"
580
    mcall    MF_DELAY, 7
581
    call    getCurrentIndex
582
    test    al, BIT0
583
    jnz    @b	    ; loop if not ready yet
584
;        print   "fb"
585
 
586
    cmp    [status], ST_PLAY
587
    jne    .exit
588
 
589
    call    updateLVI
590
 
591
    mov    eax, 1
592
    call    update_next_buffer
593
    test    al, al
594
    jnz    .exit_wait
595
 
596
    jmp    .tuneLoop
597
   .exit_wait:
598
    mcall    MF_DELAY, 30 ; a little pause - let the player finish
599
   .exit:
600
ret
601
attempts db 0
602
 
603
buffers dd WAV_BUFFER1, WAV_BUFFER2
604
jumpto	  dd play.tuneLoop, play.tuneLoop1
605
 
606
 
607
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
608
;; update_first_buffer - load a chunk into the first buffer, increments offset
609
;; in:  eax = number - 0 or 1
610
;; out: error code, 0 - successful
611
update_next_buffer:
612
    push   esi edi
613
 
614
    movzx  edx, byte [wav_mode]
615
    mov    ecx, [blocks + edx * 4]
139 diamond 616
    mov    [fileinfo.bytes], ecx
31 halyavin 617
 
618
    mov    esi, LOAD_BUFFER
619
    mov    edi, [buffers+eax*4]
620
    push   eax              ;save buffer index
621
  start_attempts:
622
    mcall  MF_SYSTREE, fileinfo
623
    test eax, eax
624
    jz @f
139 diamond 625
        cmp     eax, 6
626
        jz      @f
31 halyavin 627
    cmp   [attempts],100
628
    je	 @f
629
    inc   [attempts]
630
    jmp   start_attempts
139 diamond 631
;    dpd eax
632
;    newline
633
;    dpd [fileinfo.first_block]
634
;    newline
31 halyavin 635
       @@:
636
;        print  " loaded!"
637
 
638
    push   eax ebx edx
639
    mov    eax,ecx
640
    xor    edx,edx
641
    imul   eax,10
642
    movzx     ebx,[difference_of_frequency_2]
643
 
644
    div    ebx
645
    mov    ecx,eax
646
 
647
;    mov   ebx,10
648
;    mov   eax,edx
649
;    xor   edx,edx
650
;    div   ebx
651
;   cmp   edx,5
652
;    jb   temp_12_7
653
;    inc   ecx
654
;  temp_12_7:
655
   cmp	 edx,0
656
    je	 temp_12_7
657
    inc   ecx
658
  temp_12_7:
659
 
660
    pop    edx ebx
661
    mov    eax,[esp+4]            ;restore buffer index
139 diamond 662
    add    [fileinfo.first_byte], ecx ; +60Kb
31 halyavin 663
    call   [convert + edx * 4]
664
;start fix for MM (4)
665
    mov    eax,[esp+4]            ;restore buffer index
666
    test   eax,not 1
667
    jz     .ok
668
    print  "buffer index out of range"
669
    dpd    eax
670
    jmp    .ret
671
  .ok:
672
    push   ebp
673
    mov    ebp,[phys_wav_buffer1+eax*4]
674
    mov    edi,[buffers+eax*4]
675
    mcall  MF_INTERNAL_SERVICES,SET_PHYS_BUFFER,ebp,edi,60*1024
676
    pop    ebp
677
.ret:
678
    pop    eax
679
    add    esp,4                  ;pop buffer index
680
;end fix for MM (4)
681
 
682
    pop    edi esi
683
ret
684
 
685
c8mono:
686
    mov   [type_of_conversion],1
687
    jmp   for_all_type
688
 
689
c8mono_1:
690
    lodsb
691
    call  c8mono_2
692
    push  ax
693
    shl   eax,16
694
    pop   ax
695
    push  eax
696
    mov al,[esi]
697
    call  c8mono_2
698
    push  ax
699
    shl   eax,16
700
    pop   ax
701
    mov  ebx,eax
702
    pop  eax
703
    jmp  for_all_type_1
704
 
705
c8mono_2:
706
    sub    al, 0x80
707
    cbw
708
    imul   ax, 255
709
    ret
710
 
711
c8stereo:
712
    mov   [type_of_conversion],2
713
    jmp   for_all_type
714
 
715
c8stereo_1:
716
    lodsb
717
    call  c8stereo_2
718
    shl eax,16
719
    lodsb
720
    call  c8stereo_2
721
    push  eax
722
    mov al,[esi]
723
    call  c8stereo_2
724
    shl eax,16
725
    mov al,[esi+1]
726
    call  c8stereo_2
727
    mov   ebx,eax
728
    pop  eax
729
    jmp   for_all_type_1
730
 
731
c8stereo_2:
732
    sub    al, 0x80
733
    cbw
734
    imul   ax, 255
735
    ret
736
 
737
c16mono:
738
    mov   [type_of_conversion],3
739
    jmp   for_all_type
740
 
741
c16mono_1:
742
	lodsw
743
	push  ax
744
	shl eax,16
745
	pop   ax
746
	mov bx,[esi]
747
	shl ebx,16
748
	mov bx,[esi]
749
	jmp  for_all_type_1
750
 
751
c16stereo:
752
 for_all_type:
753
    xor   edx,edx
754
    mov    eax, 15*1024*10
755
    movzx     ebx,[difference_of_frequency_2]
756
    xor    edx,edx
757
    div    ebx
758
    mov    ecx,eax
759
 
760
;    mov   ebx,10
761
;    mov   eax,edx
762
;    xor   edx,edx
763
;    div   ebx
764
;    cmp   edx,5
765
;    jb   temp_12_6
766
;    inc   ecx
767
;  temp_12_6:
768
   cmp	 edx,0
769
    je	 temp_12_6
770
    inc   ecx
771
  temp_12_6:
772
 
773
  c16stereo_1:
774
    mov  [znak],0
775
 
776
    cmp  [type_of_conversion],1
777
    je	 c8mono_1
778
    cmp  [type_of_conversion],2
779
    je	 c8stereo_1
780
    cmp  [type_of_conversion],3
781
    je	 c16mono_1
782
    lodsd
783
 
784
    mov ebx,[esi]
785
for_all_type_1:
786
    cmp eax,ebx
787
    jne  c16stereo_2
788
    inc  [znak]
789
    c16stereo_2:
790
    push eax
791
    push ecx
792
    sub  eax,ebx
793
    push eax
794
    shl  eax,16
795
    movzx  ebx,[difference_of_frequency]
796
    inc   ebx
797
    xor  edx,edx
798
    div  ebx
799
    shr  eax,16
800
    mov  ecx,eax
801
    pop  eax
802
    xor  ax,ax
803
    xor  edx,edx
804
    div  ebx
805
    shl  eax,16
806
    mov  cx,ax
807
    mov  ebx,ecx
808
    pop  ecx
809
    pop   eax
810
    mov    dl,[difference_of_frequency]
811
    inc   dl
812
    @@:
813
temp_12:
814
    cmp   [difference_of_frequency_1],0
815
    je	  temp_12_3
816
    cmp   [difference_of_frequency_1],5
817
    jne   temp_12_4
818
    cmp  [difference_of_frequency_4],2
819
    jne  temp_12_3
820
    jmp  temp_12_5
821
 temp_12_4:
822
    cmp  [difference_of_frequency_4],10
823
    jne  temp_12_3
824
 
825
 temp_12_5:
826
 
827
    cmp  [znak],0
828
    jne   temp_12_5_1
829
    sub  eax,ebx
830
    jmp  temp_12_5_2
831
 temp_12_5_1:
832
    add  eax,ebx
833
 temp_12_5_2:
834
 
835
 
836
    stosd
837
    inc  [schetchik]
838
    mov    [difference_of_frequency_4],0
839
 temp_12_3:
840
    cmp  [znak],0
841
    jne   temp_13
842
    sub  eax,ebx
843
    jmp  temp_14
844
 temp_13:
845
    add  eax,ebx
846
 
847
 temp_14:
848
    cld
849
    dec    dl
850
    jz	  temp_14_1
851
    stosd
852
    inc   [schetchik]
853
    inc   [difference_of_frequency_4]
854
    jmp   temp_12
855
 temp_14_1:
856
    dec    ecx
857
    cmp   ecx,0
858
;    jnz    c16stereo_1
859
    jg	  c16stereo_1
860
    newline
861
    dph [schetchik]
862
 temp_14_2:
863
    cmp   [schetchik],15360
864
    jge   temp_14_3
865
    stosd
866
    inc  [schetchik]
867
    jmp  temp_14_2
868
 
869
  temp_14_3:
870
    newline
871
    dph [schetchik]
872
    cmp   [schetchik],15360
873
    je	  temp_14_4
874
;    mov  [edi-4],dword 0
875
    sub   edi,4
876
;    sub   esi,4
877
 temp_14_4:
878
    mov   [schetchik],0
879
    ret
880
 
881
 
882
difference_of_frequency db 0
883
difference_of_frequency_1 db 0
884
difference_of_frequency_2 db 0
885
difference_of_frequency_4 db 0
886
schetchik dd 0
887
znak db 0
888
type_of_conversion db 0
889
 
890
convert dd c8mono, c8stereo, c16mono, c16stereo
139 diamond 891
blocks	  dd 30*512, 60*512, 60*512, 120*512
31 halyavin 892
 
893
 
894
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
895
;; get_my_address - get base address of the program in physical memory
896
;;   in:  nothing
897
;;   out: eax = address
898
;start fix for MM (8)
899
;function shouldn't used.
900
;get_my_address:
901
;    pushad
902
;    mcall    MF_PROCINFO, procinfo, PN_MYSELF
903
;    popad
904
;    mov    eax, [procinfo.memory_start]
905
;ret
906
;end fix for MM (8)
907
 
908
 
909
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
910
;; set the last valid index to something other than we're currently playing
911
;; so that we never end
912
;;
913
;; this routine just sets the last valid index to 1 less than the index
914
;; that we're currently playing, thus keeping it in and endless loop
915
;; input:  none
916
;; output: none
917
updateLVI:
918
    push    eax
919
    call    getCurrentIndex
920
     ; dps "index "
921
     ; dpd eax
922
     ; newline
923
    dec    al
924
    and    al, INDEX_MASK
925
    call    setLastValidIndex
926
    pop    eax
927
ret
928
 
929
;---------------------------------------------------------------------
930
 
931
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
932
;; returns AL = current index value
933
getCurrentIndex:
934
    push    edx
935
    mov    edx, PO_CIV_REG
936
    call    NABMBAR_read_byte
937
    pop    edx
938
ret
939
 
940
;---------------------------------------------------------------------
941
 
942
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
943
;; input AL = index # to stop on
944
setLastValidIndex:
945
    push    edx
946
    mov    edx, PO_LVI_REG
947
    call    NABMBAR_write_byte
948
    pop    edx
949
ret
950
 
951
;---------------------------------------------------------------------
952
 
953
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
954
;; print_info - outputs debug information
955
;;  in:  nothing
956
;;  out: nothing
957
print_info:
958
    dps    "BUS: "
959
    movzx    eax, [bus]
960
    dph    eax
961
 
962
    dps    " DEVFN: "
963
    movzx    eax, [devfn]
964
    dph    eax
965
 
966
    dps    " IRQ: "
967
    movzx    eax, [AC97IRQ]
968
    dpd    eax
969
    newline
970
 
971
 
972
    dps    "CODEC_POWER_CTRL: "
973
    mov    edx, CODEC_POWER_CTRL_REG
974
    call    NAMBAR_read_word
975
    dph    eax
976
    dps    " (bits 0-3 should be set)"
977
    newline
978
 
979
    mov    edx, 0x28
980
    call    NAMBAR_read_word
981
    dph    eax
982
    dps    " - supported features"
983
    newline
984
    mov    edx, 0x2A
985
    call    NAMBAR_read_word
986
    dph    eax
987
    dps    " - config"
988
    newline
989
    mov    edx, 0x2C
990
    call    NAMBAR_read_word
991
    dph    eax
992
    dps    " - PCM rate"
993
 
994
    newline
995
ret
996
 
997
 
998
;---------------------------------------------------------------------
999
;---  DATA OF PROGRAM  -----------------------------------------------
1000
;---------------------------------------------------------------------
1001
volume		 dd  15
1002
 
139 diamond 1003
attrinfo:
1004
        dd      5
1005
        dd      0
1006
        dd      0
1007
        dd      0
1008
        dd      fileattr
1009
        db      0
1010
        dd      textbox_string
1011
 
31 halyavin 1012
fileinfo:
139 diamond 1013
 .mode          dd      0		 ; READ
1014
 .first_byte    dd      0
1015
                dd      0
1016
 .bytes         dd      60*1024		 ; 60 Kb
31 halyavin 1017
 .dest		 dd  LOAD_BUFFER ;file_data
1018
	 ;  db  "/HD/1/WINDOWS/MEDIA/WICEB7~1.WAV",0
1019
;sz textbox_string, "/hd/1/testmuz/menuet11.wav",0
139 diamond 1020
textbox_string:
31 halyavin 1021
;---------------------------------------------------------------------
1022
 
1023
IMAGE_END:		 ; end of program's image
139 diamond 1024
   rb 257
1025
;   rb 257-textbox_string.size
31 halyavin 1026
;     textbox_string.size
1027
 
1028
;---------------------------------------------------------------------
1029
 
1030
device_id dd ?	  ; (device_id << 16) + vendor_id
1031
lastbus   db ?	  ; pci coordinates
1032
bus	 db ?
1033
devfn	   db ?
1034
 
1035
AC97ICH4  db ?	  ; Intel ICH4 codec flag
1036
SI7012	    db ?    ; SiS SI7012 codec flag
1037
NAMBAR	    dw ?    ; Audio Mixers Registers (base)
1038
NABMBAR   dw ?	  ; Bus Master Registers   (base)
1039
 
1040
AC97IRQ   db ?	  ; Interrupt request
1041
AC97INT   db ?	  ; Interrupt pin
1042
 
1043
wav_mode  db ?	  ; bits per sample & channels
1044
 
1045
;---------------------------------------------------------------------
1046
 
1047
ST_DONE = 0x0	 ; for interacting with player's window
1048
ST_PLAY = 0x1
1049
ST_EXIT = 0x2
1050
ST_STOP = 0x4
1051
 
1052
status	    db ?
1053
 
139 diamond 1054
fileattr: rb 40
1055
 
31 halyavin 1056
;---------------------------------------------------------------------
1057
phys_bdl_buffer rd 1
1058
phys_wav_buffer1 rd 1
1059
phys_wav_buffer2 rd 1
1060
align 32
1061
 
1062
 
1063
; Buffer Descriptors List
1064
;  ___________________________
1065
;  |     physical address    | dword
1066
;  |_________________________|
1067
;  | attr       |   length   | dword     max. length = 65535 samples
1068
;  |_________________________|
1069
 
1070
BDL_BUFFER:
1071
 rb 32*8     ; 32 descriptors, 8 bytes each
1072
 
1073
 
1074
;---------------------------------------------------------------------
1075
 
1076
file_data:
1077
 
1078
WAV_BUFFER1:
1079
 rb 60 * 1024  ; 60 Kb
1080
 
1081
WAV_BUFFER2:
1082
 rb 60 * 1024
1083
 
1084
LOAD_BUFFER:
1085
 rb 60 * 1024
1086
 
1087
;---------------------------------------------------------------------
1088
 
1089
procinfo process_information
1090
 
1091
work_area:
1092
 rb 0x10000
1093
 
1094
;---------------------------------------------------------------------
1095
 
1096
rb 0x800
1097
thread_stack:
1098
 
1099
rb 0x1000 ; for stack
1100
STACK_P:
1101
 
1102
MEMORY_END: