-
Notifications
You must be signed in to change notification settings - Fork 1
/
playwav.txt
1675 lines (1675 loc) · 91.9 KB
/
playwav.txt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
1 ; ****************************************************************************
2 ; playwav.s (for TRDOS 386)
3 ; ----------------------------------------------------------------------------
4 ; PLAYWAV.PRG ! Sound Blaster 16 .wav player program by Erdogan TAN
5 ;
6 ; 07/03/2017
7 ;
8 ; [ Last Modification: 20/10/2017 ]
9 ;
10 ; Modified from TINYPLAY.PRG .mod player program by Erdogan Tan, 04/03/2017
11 ;
12 ; Derived from source code of 'PLAYWAV.COM' ('PLAYWAV.ASM') by Erdogan Tan
13 ; (17/02/2017)
14 ; Assembler: NASM version 2.11
15 ; nasm playwav.s -l playwav.txt -o PLAYWAV.PRG
16 ; ----------------------------------------------------------------------------
17 ; Derived from '.wav file player for DOS' Jeff Leyda, Sep 02, 2002
18
19
20 ; 01/03/2017
21 ; 16/10/2016
22 ; 29/04/2016
23 ; TRDOS 386 system calls (temporary list!)
24 _ver equ 0
25 _exit equ 1
26 _fork equ 2
27 _read equ 3
28 _write equ 4
29 _open equ 5
30 _close equ 6
31 _wait equ 7
32 _creat equ 8
33 _link equ 9
34 _unlink equ 10
35 _exec equ 11
36 _chdir equ 12
37 _time equ 13
38 _mkdir equ 14
39 _chmod equ 15
40 _chown equ 16
41 _break equ 17
42 _stat equ 18
43 _seek equ 19
44 _tell equ 20
45 _mount equ 21
46 _umount equ 22
47 _setuid equ 23
48 _getuid equ 24
49 _stime equ 25
50 _quit equ 26
51 _intr equ 27
52 _fstat equ 28
53 _emt equ 29
54 _mdate equ 30
55 _video equ 31
56 _audio equ 32
57 _timer equ 33
58 _sleep equ 34
59 _msg equ 35
60 _geterr equ 36
61 _fpsave equ 37
62 _pri equ 38
63 _rele equ 39
64 _fff equ 40
65 _fnf equ 41
66 _alloc equ 42
67 _dalloc equ 43
68 _calbac equ 44
69
70 %macro sys 1-4
71 ; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
72 ; 03/09/2015
73 ; 13/04/2015
74 ; Retro UNIX 386 v1 system call.
75 %if %0 >= 2
76 mov ebx, %2
77 %if %0 >= 3
78 mov ecx, %3
79 %if %0 = 4
80 mov edx, %4
81 %endif
82 %endif
83 %endif
84 mov eax, %1
85 ;int 30h
86 int 40h ; TRDOS 386 (TRDOS v2.0)
87 %endmacro
88
89 ; TRDOS 386 (and Retro UNIX 386 v1) system call format:
90 ; sys systemcall (eax) <arg1 (ebx)>, <arg2 (ecx)>, <arg3 (edx)>
91
92
93 [BITS 32]
94
95 [ORG 0]
96
97 _STARTUP:
98 ; Prints the Credits Text.
99 sys _msg, Credits, 255, 0Bh
99 <1>
99 <1>
99 <1>
99 <1>
99 <1> %if %0 >= 2
99 00000000 BB[18070000] <1> mov ebx, %2
99 <1> %if %0 >= 3
99 00000005 B9FF000000 <1> mov ecx, %3
99 <1> %if %0 = 4
99 0000000A BA0B000000 <1> mov edx, %4
99 <1> %endif
99 <1> %endif
99 <1> %endif
99 0000000F B823000000 <1> mov eax, %1
99 <1>
99 00000014 CD40 <1> int 40h
100
101 ; clear bss
102 00000016 B9[00000200] mov ecx, EOF
103 0000001B BF[DB070000] mov edi, bss_start
104 00000020 29F9 sub ecx, edi
105 00000022 D1E9 shr ecx, 1
106 00000024 31C0 xor eax, eax
107 00000026 F366AB rep stosw
108
109 GetFileName:
110 00000029 89E6 mov esi, esp
111 0000002B AD lodsd
112 0000002C 83F802 cmp eax, 2 ; two arguments
113 ; (program file name & mod file name)
114 0000002F 0F82EA000000 jb pmsg_usage ; nothing to do
115
116 00000035 AD lodsd ; program file name address
117 00000036 AD lodsd ; mod file name address (file to be read)
118 00000037 89C6 mov esi, eax
119 00000039 BF[02080000] mov edi, wav_file_name
120 ScanName:
121 0000003E AC lodsb
122 0000003F 84C0 test al, al
123 00000041 0F84D8000000 je pmsg_usage
124 00000047 3C20 cmp al, 20h
125 00000049 74F3 je short ScanName ; scan start of name.
126 0000004B AA stosb
127 0000004C B4FF mov ah, 0FFh
128 a_0:
129 0000004E FEC4 inc ah
130 a_1:
131 00000050 AC lodsb
132 00000051 AA stosb
133 00000052 3C2E cmp al, '.'
134 00000054 74F8 je short a_0
135 00000056 20C0 and al, al
136 00000058 75F6 jnz short a_1
137
138 0000005A 08E4 or ah, ah ; if period NOT found,
139 0000005C 750B jnz short a_2 ; then add a .WAV extension.
140 SetExt:
141 0000005E 4F dec edi
142 0000005F C7072E574156 mov dword [edi], '.WAV'
143 00000065 C6470400 mov byte [edi+4], 0
144 a_2:
145 00000069 E8E1000000 call DetectSb ; Detect the SB Addr, Irq.
146
147 ; DIRECT CGA (TEXT MODE) MEMORY ACCESS
148 ; bl = 0, bh = 4
149 ; Direct access/map to CGA (Text) memory (0B8000h)
150
151 sys _video, 0400h
151 <1>
151 <1>
151 <1>
151 <1>
151 <1> %if %0 >= 2
151 0000006E BB00040000 <1> mov ebx, %2
151 <1> %if %0 >= 3
151 <1> mov ecx, %3
151 <1> %if %0 = 4
151 <1> mov edx, %4
151 <1> %endif
151 <1> %endif
151 <1> %endif
151 00000073 B81F000000 <1> mov eax, %1
151 <1>
151 00000078 CD40 <1> int 40h
152 0000007A 3D00800B00 cmp eax, 0B8000h
153 0000007F 0F85B2000000 jne error_exit
154
155 ; open the file
156 ; open existing file
157 00000085 E86D020000 call openFile ; no error? ok.
158 0000008A 7318 jnc short _gsr
159
160 ; file not found!
161 sys _msg, noFileErrMsg, 255, 0Fh
161 <1>
161 <1>
161 <1>
161 <1>
161 <1> %if %0 >= 2
161 0000008C BB[48070000] <1> mov ebx, %2
161 <1> %if %0 >= 3
161 00000091 B9FF000000 <1> mov ecx, %3
161 <1> %if %0 = 4
161 00000096 BA0F000000 <1> mov edx, %4
161 <1> %endif
161 <1> %endif
161 <1> %endif
161 0000009B B823000000 <1> mov eax, %1
161 <1>
161 000000A0 CD40 <1> int 40h
162 000000A2 EB72 jmp Exit
163
164 _gsr:
165 000000A4 E87E020000 call getSampleRate ; read the sample rate
166 ; pass it onto codec.
167 000000A9 726B jc Exit
168
169 000000AB 66A3[F8070000] mov [sampling_rate], ax
170 000000B1 880D[FA070000] mov [stmo], cl
171 000000B7 8815[FC070000] mov [bps], dl
172
173 PlayNow:
174 ; DIRECT MEMORY ACCESS (for Audio DMA)
175 ; ebx = DMA buffer address (virtual, user)
176 ; ecx = buffer size (in bytes)
177 ; edx = upper limit = 16MB
178
179 _16MB equ 1024*1024*16
180
181 sys _alloc, DmaBuffer, DmaBufSize, _16MB
181 <1>
181 <1>
181 <1>
181 <1>
181 <1> %if %0 >= 2
181 000000BD BB[00000100] <1> mov ebx, %2
181 <1> %if %0 >= 3
181 000000C2 B900000100 <1> mov ecx, %3
181 <1> %if %0 = 4
181 000000C7 BA00000001 <1> mov edx, %4
181 <1> %endif
181 <1> %endif
181 <1> %endif
181 000000CC B82A000000 <1> mov eax, %1
181 <1>
181 000000D1 CD40 <1> int 40h
182 000000D3 7262 jc short error_exit
183
184 000000D5 A3[12080000] mov [DMA_phy_buff], eax ; physical address
185 ; of the buffer
186 ; (which is needed
187 ; for DMA controller)
188 000000DA E8A6020000 call SbInit
189 ;
190 ; position file pointer to start in actual wav data
191 ; MUCH improvement should really be done here to check if sample size is
192 ; supported, make sure there are 2 channels, etc.
193 ;
194 ;mov ah, 42h
195 ;mov al, 0 ; from start of file
196 ;mov bx, [FileHandle]
197 ;xor cx, cx
198 ;mov dx, 44 ; jump past .wav/riff header
199 ;int 21h
200
201 sys _seek, [FileHandle], 44, 0
201 <1>
201 <1>
201 <1>
201 <1>
201 <1> %if %0 >= 2
201 000000DF 8B1D[D7070000] <1> mov ebx, %2
201 <1> %if %0 >= 3
201 000000E5 B92C000000 <1> mov ecx, %3
201 <1> %if %0 = 4
201 000000EA BA00000000 <1> mov edx, %4
201 <1> %endif
201 <1> %endif
201 <1> %endif
201 000000EF B813000000 <1> mov eax, %1
201 <1>
201 000000F4 CD40 <1> int 40h
202
203 ; play the .wav file. Most of the good stuff is in here.
204
205 000000F6 E8A5050000 call PlayWav
206
207 ; close the .wav file and exit.
208
209 000000FB E810020000 call closeFile
210
211 00000100 E819050000 call SbDone
212
213 ; Deallocate DMA buffer (not necessary just before exit!)
214 sys _dalloc, DmaBuffer, DmaBufSize
214 <1>
214 <1>
214 <1>
214 <1>
214 <1> %if %0 >= 2
214 00000105 BB[00000100] <1> mov ebx, %2
214 <1> %if %0 >= 3
214 0000010A B900000100 <1> mov ecx, %3
214 <1> %if %0 = 4
214 <1> mov edx, %4
214 <1> %endif
214 <1> %endif
214 <1> %endif
214 0000010F B82B000000 <1> mov eax, %1
214 <1>
214 00000114 CD40 <1> int 40h
215 ;jc error_exit
216 Exit:
217 sys _exit ; Bye!
217 <1>
217 <1>
217 <1>
217 <1>
217 <1> %if %0 >= 2
217 <1> mov ebx, %2
217 <1> %if %0 >= 3
217 <1> mov ecx, %3
217 <1> %if %0 = 4
217 <1> mov edx, %4
217 <1> %endif
217 <1> %endif
217 <1> %endif
217 00000116 B801000000 <1> mov eax, %1
217 <1>
217 0000011B CD40 <1> int 40h
218
219 here:
220 0000011D EBFE jmp short here
221
222 pmsg_usage:
223 sys _msg, msg_usage, 255, 0Bh
223 <1>
223 <1>
223 <1>
223 <1>
223 <1> %if %0 >= 2
223 0000011F BB[F0060000] <1> mov ebx, %2
223 <1> %if %0 >= 3
223 00000124 B9FF000000 <1> mov ecx, %3
223 <1> %if %0 = 4
223 00000129 BA0B000000 <1> mov edx, %4
223 <1> %endif
223 <1> %endif
223 <1> %endif
223 0000012E B823000000 <1> mov eax, %1
223 <1>
223 00000133 CD40 <1> int 40h
224 00000135 EBDF jmp short Exit
225
226 error_exit:
227 sys _msg, trdos386_err_msg, 255, 0Eh
227 <1>
227 <1>
227 <1>
227 <1>
227 <1> %if %0 >= 2
227 00000137 BB[B7070000] <1> mov ebx, %2
227 <1> %if %0 >= 3
227 0000013C B9FF000000 <1> mov ecx, %3
227 <1> %if %0 = 4
227 00000141 BA0E000000 <1> mov edx, %4
227 <1> %endif
227 <1> %endif
227 <1> %endif
227 00000146 B823000000 <1> mov eax, %1
227 <1>
227 0000014B CD40 <1> int 40h
228 0000014D EBC7 jmp short Exit
229
230 DetectSb:
231 0000014F 60 pushad
232 ScanPort:
233 00000150 66BB1002 mov bx, 210h ; start scanning ports
234 ; 210h, 220h, .. 260h
235 ResetDSP:
236 00000154 6689DA mov dx, bx ; try to reset the DSP.
237 00000157 6683C206 add dx, 06h
238 0000015B B001 mov al, 1
239 ;out dx, al
240 0000015D B401 mov ah, 1 ; outb
241 0000015F CD34 int 34h
242
243 ;in al, dx
244 ;in al, dx
245 ;in al, dx
246 ;in al, dx
247
248 00000161 B400 mov ah, 0 ; inb
249 00000163 CD34 int 34h
250 ;mov ah, 0 ; inb
251 00000165 CD34 int 34h
252
253 00000167 30C0 xor al, al
254 ;out dx, al
255 00000169 B401 mov ah, 1 ; outb
256 0000016B CD34 int 34h
257
258 0000016D 6683C208 add dx, 08h
259 ;mov cx, 100
260 00000171 66B92000 mov cx, 32
261 00000175 28E4 sub ah, ah ; 0
262 WaitID:
263 ;in al, dx
264 00000177 CD34 int 34h ;ah = 0 ; inb
265 00000179 08C0 or al, al
266 0000017B 7804 js short GetID
267 0000017D E2F8 loop WaitID
268 0000017F EB10 jmp short NextPort
269 GetID:
270 00000181 6683EA04 sub dx, 04h
271 ;in al, dx
272 00000185 CD34 int 34h ;ah = 0 ; inb
273 00000187 3CAA cmp al, 0AAh
274 00000189 7416 je short Found
275 0000018B 6683C204 add dx, 04h
276 0000018F E2E6 loop WaitID
277 NextPort:
278 00000191 6683C310 add bx, 10h ; if not response,
279 00000195 6681FB6002 cmp bx, 260h ; try the next port.
280 0000019A 76B8 jbe short ResetDSP
281 0000019C E934010000 jmp Fail
282 Found:
283 000001A1 66891D[EC060000] mov [SbAddr], bx ; SB Port Address Found!
284 ScanIRQ:
285 SetIrqs:
286 ; LINK SIGNAL RESPONSE/RETURN BYTE TO REQUESTED IRQ
287 sys _calbac, 102h, 2, SbIrq ; IRQ 2
287 <1>
287 <1>
287 <1>
287 <1>
287 <1> %if %0 >= 2
287 000001A8 BB02010000 <1> mov ebx, %2
287 <1> %if %0 >= 3
287 000001AD B902000000 <1> mov ecx, %3
287 <1> %if %0 = 4
287 000001B2 BA[EE060000] <1> mov edx, %4
287 <1> %endif
287 <1> %endif
287 <1> %endif
287 000001B7 B82C000000 <1> mov eax, %1
287 <1>
287 000001BC CD40 <1> int 40h
288 ; Signal Response Byte
289 ;jc short error_exit
290
291 sys _calbac, 103h, 3, SbIrq ; IRQ 3
291 <1>
291 <1>
291 <1>
291 <1>
291 <1> %if %0 >= 2
291 000001BE BB03010000 <1> mov ebx, %2
291 <1> %if %0 >= 3
291 000001C3 B903000000 <1> mov ecx, %3
291 <1> %if %0 = 4
291 000001C8 BA[EE060000] <1> mov edx, %4
291 <1> %endif
291 <1> %endif
291 <1> %endif
291 000001CD B82C000000 <1> mov eax, %1
291 <1>
291 000001D2 CD40 <1> int 40h
292 ; Signal Response Byte
293 ;jc short error_exit
294
295 sys _calbac, 104h, 4, SbIrq ; IRQ 4
295 <1>
295 <1>
295 <1>
295 <1>
295 <1> %if %0 >= 2
295 000001D4 BB04010000 <1> mov ebx, %2
295 <1> %if %0 >= 3
295 000001D9 B904000000 <1> mov ecx, %3
295 <1> %if %0 = 4
295 000001DE BA[EE060000] <1> mov edx, %4
295 <1> %endif
295 <1> %endif
295 <1> %endif
295 000001E3 B82C000000 <1> mov eax, %1
295 <1>
295 000001E8 CD40 <1> int 40h
296 ; Signal Response Byte
297 ;jc short error_exit
298
299 sys _calbac, 105h, 5, SbIrq ; IRQ 5
299 <1>
299 <1>
299 <1>
299 <1>
299 <1> %if %0 >= 2
299 000001EA BB05010000 <1> mov ebx, %2
299 <1> %if %0 >= 3
299 000001EF B905000000 <1> mov ecx, %3
299 <1> %if %0 = 4
299 000001F4 BA[EE060000] <1> mov edx, %4
299 <1> %endif
299 <1> %endif
299 <1> %endif
299 000001F9 B82C000000 <1> mov eax, %1
299 <1>
299 000001FE CD40 <1> int 40h
300 ; Signal Response Byte
301 ;jc short error_exit
302
303 sys _calbac, 107h, 7, SbIrq ; IRQ 7
303 <1>
303 <1>
303 <1>
303 <1>
303 <1> %if %0 >= 2
303 00000200 BB07010000 <1> mov ebx, %2
303 <1> %if %0 >= 3
303 00000205 B907000000 <1> mov ecx, %3
303 <1> %if %0 = 4
303 0000020A BA[EE060000] <1> mov edx, %4
303 <1> %endif
303 <1> %endif
303 <1> %endif
303 0000020F B82C000000 <1> mov eax, %1
303 <1>
303 00000214 CD40 <1> int 40h
304 ; Signal Response Byte
305 ;jc short error_exit
306
307 00000216 C605[EE060000]00 mov byte [SbIrq], 0 ; clear the IRQ level.
308
309 0000021D 668B15[EC060000] mov dx, [SbAddr] ; tells to the SB to
310 00000224 6683C20C add dx, 0Ch ; generate a IRQ!
311 WaitSb:
312 ;in al, dx
313 00000228 B400 mov ah, 0 ; inb
314 0000022A CD34 int 34h
315 0000022C 08C0 or al, al
316 0000022E 78F8 js short WaitSb
317 00000230 B0F2 mov al, 0F2h
318 ;out dx, al
319 00000232 B401 mov ah,1 ; outb
320 00000234 CD34 int 34h
321
322 00000236 31C9 xor ecx, ecx ; wait until IRQ level
323 WaitIRQ:
324 00000238 803D[EE060000]00 cmp byte [SbIrq], 0 ; is changed or timeout.
325 0000023F 7506 jne short IrqOk
326 00000241 6649 dec cx
327 00000243 75F3 jnz short WaitIRQ
328 00000245 EB0F jmp short RestoreIrqs
329 IrqOk:
330 00000247 668B15[EC060000] mov dx, [SbAddr]
331 0000024E 6683C20E add dx, 0Eh
332 ;in al, dx ; SB acknowledge.
333 00000252 B400 mov ah, 0 ; inb
334 00000254 CD34 int 34h
335 ;mov al, 20h
336 ;;out 20h, al ; Hardware acknowledge.
337 ;mov ah,1 ; outb
338 ;int 34h
339
340 RestoreIrqs:
341 ; UNLINK SIGNAL RESPONSE/RETURN BYTE FROM REQUESTED IRQ
342 sys _calbac, 2 ; unlink IRQ 2
342 <1>
342 <1>
342 <1>
342 <1>
342 <1> %if %0 >= 2
342 00000256 BB02000000 <1> mov ebx, %2
342 <1> %if %0 >= 3
342 <1> mov ecx, %3
342 <1> %if %0 = 4
342 <1> mov edx, %4
342 <1> %endif
342 <1> %endif
342 <1> %endif
342 0000025B B82C000000 <1> mov eax, %1
342 <1>
342 00000260 CD40 <1> int 40h
343 ; Signal Response Byte
344 sys _calbac, 3 ; unlink IRQ 3
344 <1>
344 <1>
344 <1>
344 <1>
344 <1> %if %0 >= 2
344 00000262 BB03000000 <1> mov ebx, %2
344 <1> %if %0 >= 3
344 <1> mov ecx, %3
344 <1> %if %0 = 4
344 <1> mov edx, %4
344 <1> %endif
344 <1> %endif
344 <1> %endif
344 00000267 B82C000000 <1> mov eax, %1
344 <1>
344 0000026C CD40 <1> int 40h
345 ; Signal Response Byte
346 sys _calbac, 4 ; unlink IRQ 4
346 <1>
346 <1>
346 <1>
346 <1>
346 <1> %if %0 >= 2
346 0000026E BB04000000 <1> mov ebx, %2
346 <1> %if %0 >= 3
346 <1> mov ecx, %3
346 <1> %if %0 = 4
346 <1> mov edx, %4
346 <1> %endif
346 <1> %endif
346 <1> %endif
346 00000273 B82C000000 <1> mov eax, %1
346 <1>
346 00000278 CD40 <1> int 40h
347 ; Signal Response Byte
348 sys _calbac, 5 ; unlink IRQ 5
348 <1>
348 <1>
348 <1>
348 <1>
348 <1> %if %0 >= 2
348 0000027A BB05000000 <1> mov ebx, %2
348 <1> %if %0 >= 3
348 <1> mov ecx, %3
348 <1> %if %0 = 4
348 <1> mov edx, %4
348 <1> %endif
348 <1> %endif
348 <1> %endif
348 0000027F B82C000000 <1> mov eax, %1
348 <1>
348 00000284 CD40 <1> int 40h
349 ; Signal Response Byte
350 sys _calbac, 7 ; unlink IRQ 7
350 <1>
350 <1>
350 <1>
350 <1>
350 <1> %if %0 >= 2
350 00000286 BB07000000 <1> mov ebx, %2
350 <1> %if %0 >= 3
350 <1> mov ecx, %3
350 <1> %if %0 = 4
350 <1> mov edx, %4
350 <1> %endif
350 <1> %endif
350 <1> %endif
350 0000028B B82C000000 <1> mov eax, %1
350 <1>
350 00000290 CD40 <1> int 40h
351 ; Signal Response Byte
352
353 00000292 803D[EE060000]00 cmp byte [SbIrq], 0 ; IRQ level was changed?
354 00000299 743A je short Fail ; no, fail.
355 Success:
356 0000029B 668B15[EC060000] mov dx, [SbAddr] ; Print Sucessful message.
357 000002A2 8A0D[EE060000] mov cl, [SbIrq]
358 000002A8 C0EA04 shr dl, 4
359 000002AB 80C230 add dl, '0'
360 000002AE 8815[A9070000] mov [PortText], dl
361 000002B4 80C130 add cl, '0'
362 000002B7 880D[B2070000] mov [IrqText], cl
363
364 sys _msg, MsgFound, 255, 0Fh
364 <1>
364 <1>
364 <1>
364 <1>
364 <1> %if %0 >= 2
364 000002BD BB[89070000] <1> mov ebx, %2
364 <1> %if %0 >= 3
364 000002C2 B9FF000000 <1> mov ecx, %3
364 <1> %if %0 = 4
364 000002C7 BA0F000000 <1> mov edx, %4
364 <1> %endif
364 <1> %endif
364 <1> %endif
364 000002CC B823000000 <1> mov eax, %1
364 <1>
364 000002D1 CD40 <1> int 40h
365
366 000002D3 61 popad ; Return to caller.
367 000002D4 C3 retn
368
369 Fail:
370 ; Print Failed Message,
371 ; and exit to MainProg.
372
373 sys _msg, MsgNotFound, 255, 0Fh
373 <1>
373 <1>
373 <1>
373 <1>
373 <1> %if %0 >= 2
373 000002D5 BB[61070000] <1> mov ebx, %2
373 <1> %if %0 >= 3
373 000002DA B9FF000000 <1> mov ecx, %3
373 <1> %if %0 = 4
373 000002DF BA0F000000 <1> mov edx, %4
373 <1> %endif
373 <1> %endif
373 <1> %endif
373 000002E4 B823000000 <1> mov eax, %1
373 <1>
373 000002E9 CD40 <1> int 40h
374
375 sys _exit
375 <1>
375 <1>
375 <1>
375 <1>
375 <1> %if %0 >= 2
375 <1> mov ebx, %2
375 <1> %if %0 >= 3
375 <1> mov ecx, %3
375 <1> %if %0 = 4
375 <1> mov edx, %4
375 <1> %endif
375 <1> %endif
375 <1> %endif
375 000002EB B801000000 <1> mov eax, %1
375 <1>
375 000002F0 CD40 <1> int 40h
376
377 000002F2 E926FEFFFF jmp here
378
379 ;open or create file
380 ;
381 ;input: ds:dx-->filename (asciiz)
382 ; al=file Mode (create or open)
383 ;output: none cs:[FileHandle] filled
384 ;
385 openFile:
386 ;;push eax
387 ;;push ecx
388 ;mov ah, 3Bh ; start with a mode
389 ;add ah, al ; add in create or open mode
390 ;xor cx, cx
391 ;int 21h
392 ;jc short _of1
393 ;;mov [cs:FileHandle], ax
394
395 sys _open, wav_file_name, 0
395 <1>
395 <1>
395 <1>
395 <1>
395 <1> %if %0 >= 2
395 000002F7 BB[02080000] <1> mov ebx, %2
395 <1> %if %0 >= 3
395 000002FC B900000000 <1> mov ecx, %3
395 <1> %if %0 = 4
395 <1> mov edx, %4
395 <1> %endif
395 <1> %endif
395 <1> %endif
395 00000301 B805000000 <1> mov eax, %1
395 <1>
395 00000306 CD40 <1> int 40h
396 00000308 7205 jc short _of1
397
398 0000030A A3[D7070000] mov [FileHandle], eax
399 _of1:
400 ;;pop ecx
401 ;;pop eax
402 0000030F C3 retn
403
404 ; close the currently open file
405 ; input: none, uses cs:[FileHandle]
406 closeFile:
407 ;push eax
408 ;push ebx
409 00000310 833D[D7070000]FF cmp dword [FileHandle], -1
410 00000317 740D je short _cf1
411 ;mov bx, [FileHandle]
412 ;mov ax, 3E00h
413 ;int 21h ;close file
414
415 sys _close, [FileHandle]
415 <1>
415 <1>
415 <1>
415 <1>
415 <1> %if %0 >= 2
415 00000319 8B1D[D7070000] <1> mov ebx, %2
415 <1> %if %0 >= 3
415 <1> mov ecx, %3
415 <1> %if %0 = 4
415 <1> mov edx, %4
415 <1> %endif
415 <1> %endif
415 <1> %endif
415 0000031F B806000000 <1> mov eax, %1
415 <1>
415 00000324 CD40 <1> int 40h
416 _cf1:
417 ;pop ebx
418 ;pop eax
419 00000326 C3 retn
420
421 getSampleRate:
422
423 ; reads the sample rate from the .wav file.
424 ; entry: none - assumes file is already open
425 ; exit: ax = sample rate (11025, 22050, 44100, 48000)
426 ; cx = number of channels (mono=1, stereo=2)
427 ; dx = bits per sample (8, 16)
428
429 00000327 53 push ebx
430
431 ;mov ah, 42h
432 ;mov al, 0 ; from start of file
433 ;mov bx, [FileHandle]
434 ;xor cx, cx
435 ;mov dx, 08h ; "WAVE"
436 ;int 21h
437
438 sys _seek, [FileHandle], 8, 0
438 <1>
438 <1>
438 <1>
438 <1>
438 <1> %if %0 >= 2
438 00000328 8B1D[D7070000] <1> mov ebx, %2
438 <1> %if %0 >= 3
438 0000032E B908000000 <1> mov ecx, %3
438 <1> %if %0 = 4
438 00000333 BA00000000 <1> mov edx, %4
438 <1> %endif
438 <1> %endif
438 <1> %endif
438 00000338 B813000000 <1> mov eax, %1
438 <1>
438 0000033D CD40 <1> int 40h
439
440 ;mov dx, smpRBuff
441 ;mov cx, 28 ; 28 bytes
442 ;mov ah, 3fh
443 ;int 21h
444
445 sys _read, [FileHandle], smpRBuff, 28
445 <1>
445 <1>
445 <1>
445 <1>
445 <1> %if %0 >= 2
445 0000033F 8B1D[D7070000] <1> mov ebx, %2
445 <1> %if %0 >= 3
445 00000345 B9[DC070000] <1> mov ecx, %3
445 <1> %if %0 = 4
445 0000034A BA1C000000 <1> mov edx, %4
445 <1> %endif
445 <1> %endif
445 <1> %endif
445 0000034F B803000000 <1> mov eax, %1
445 <1>
445 00000354 CD40 <1> int 40h
446
447 00000356 813D[DC070000]5741- cmp dword [smpRBuff], 'WAVE'
447 0000035E 5645
448 00000360 7520 jne short gsr_stc
449
450 00000362 66833D[E8070000]01 cmp word [smpRBuff+12], 1 ; Offset 20, must be 1 (= PCM)
451 0000036A 7516 jne short gsr_stc
452
453 0000036C 668B0D[EA070000] mov cx, [smpRBuff+14] ; return num of channels in CX
454 00000373 66A1[EC070000] mov ax, [smpRBuff+16] ; return sample rate in AX
455 00000379 668B15[F6070000] mov dx, [smpRBuff+26] ; return bits per sample value in DX
456 gsr_retn:
457 00000380 5B pop ebx
458 00000381 C3 retn
459
460 gsr_stc:
461 00000382 F9 stc
462 00000383 EBFB jmp short gsr_retn
463
464 DmaBufSize equ 65536 ; 64K file buffer size.
465 ENDOFFILE equ 1 ; flag for knowing end of file
466
467 %macro SbOut 1
468 %%Wait:
469 ;in al, dx
470 mov ah, 0
471 int 34h
472 or al, al
473 js short %%Wait
474 mov al, %1
475 ;out dx, al
476 mov ah, 1
477 int 34h
478 %endmacro
479
480 SbInit:
481 00000385 60 pushad
482
483 SetBuffer:
484 ;mov byte [DmaFlag], 0
485 ; 10/03/2017
486 00000386 8B1D[12080000] mov ebx, [DMA_phy_buff] ; physical addr of DMA buff
487 0000038C B900000100 mov ecx, DmaBufSize
488
489 00000391 803D[FC070000]10 cmp byte [bps], 16
490 00000398 7543 jne short _0 ; set 8 bit DMA buffer
491
492 ; 20/10/2017
493 ; 06/10/2017 (TRDOS 386 kernel, 'audio.s', 'SbInit_play')
494
495 ; 16 bit DMA buffer setting (DMA channel 5)
496
497 ; 09/08/2017
498 ; convert byte count to word count
499 0000039A D1E9 shr ecx, 1
500 0000039C 49 dec ecx ; word count - 1
501 ; convert byte offset to word offset
502 0000039D D1EB shr ebx, 1
503
504 ; 16 bit DMA buffer setting (DMA channel 5)
505 0000039F B005 mov al, 05h ; set mask bit for channel 5 (4+1)
506 ;out 0D4h, al
507 000003A1 66BAD400 mov dx, 0D4h ; DMA mask register
508 000003A5 B401 mov ah, 1 ;outb
509 000003A7 CD34 int 34h
510
511 000003A9 30C0 xor al, al ; stops all DMA processes on selected channel
512 ;out 0D8h, al
513 000003AB B2D8 mov dl, 0D8h ; clear selected channel register
514 ;mov ah, 1 ;outb
515 000003AD CD34 int 34h
516
517 000003AF 88D8 mov al, bl ; byte 0 of DMA buffer address (physical)
518 ;out 0C4, al
519 000003B1 B2C4 mov dl, 0C4h ; DMA channel 5 port number
520 ;mov ah, 1 ;outb
521 000003B3 CD34 int 34h
522
523 000003B5 88F8 mov al, bh ; byte 1 of DMA buffer address (physical)
524 ;out 0C4h, al
525 ;mov dl, 0C4h ; DMA channel 5 port number
526 ;mov ah, 1 ;outb
527 000003B7 CD34 int 34h
528
529 ; 09/08/2017 (TRDOS 386, 'audio.s')
530 000003B9 C1EB0F shr ebx, 15 ; complete 16 bit shift
531 000003BC 80E3FE and bl, 0FEh ; clear bit 0 (not necessary, it will be ignored)
532
533 ; 13/07/2017 (89h -> 8Bh)
534 000003BF 88D8 mov al, bl ; byte 2 of DMA buffer address (physical)
535 ;out 8Bh, al
536 000003C1 B28B mov dl, 8Bh ; page register port addr for channel 5
537 ;mov ah, 1 ;outb
538 000003C3 CD34 int 34h
539
540 000003C5 88C8 mov al, cl ; low byte of DMA count - 1
541 ;out 0C6h, al
542 000003C7 B2C6 mov dl, 0C6h ; count register port addr for channel 1
543 ;mov ah, 1 ;outb
544 000003C9 CD34 int 34h
545
546 000003CB 88E8 mov al, ch ; high byte of DMA count - 1
547 ;out 0C6h, al
548 ;mov dl, 0C6h ; count register port addr for channel 1
549 ;mov ah, 1 ;outb
550 000003CD CD34 int 34h
551
552 ; channel 5, read, autoinitialized, single mode
553 ;mov al, 49h
554 000003CF B059 mov al, 59h ; 06/10/2017
555 ;out 0D6h, al
556 000003D1 B2D6 mov dl, 0D6h ; DMA mode register port address
557 ;mov ah, 1 ;outb
558 000003D3 CD34 int 34h
559
560 000003D5 B001 mov al, 01h ; clear mask bit for channel 1
561 ;out 0D4h, al
562 000003D7 B2D4 mov dl, 0D4h ; DMA mask register port address
563 ;mov ah, 1 ;outb
564 000003D9 CD34 int 34h
565
566 000003DB EB3A jmp short ClearBuffer
567 _0:
568 000003DD 49 dec ecx ; 20/10/2017
569
570 ; 8 bit DMA buffer setting (DMA channel 1)
571 000003DE B005 mov al, 05h ; set mask bit for channel 1 (4+1)
572 ;out 0Ah, al
573 000003E0 66BA0A00 mov dx, 0Ah ; DMA mask register
574 000003E4 B401 mov ah, 1 ;outb
575 000003E6 CD34 int 34h
576
577 000003E8 30C0 xor al, al ; stops all DMA processes on selected channel
578 ;out 0Ch, al
579 000003EA B20C mov dl, 0Ch ; clear selected channel register
580 ;mov ah, 1 ;outb
581 000003EC CD34 int 34h
582
583 000003EE 88D8 mov al, bl ; byte 0 of DMA buffer address (physical)