source: trunk/src/winmm/mcicda/os2cdrom.cpp@ 21916

Last change on this file since 21916 was 21916, checked in by dmik, 14 years ago

Merge branch gcc-kmk to trunk.

File size: 12.3 KB
Line 
1/* -*- tab-width: 8; c-basic-offset: 4 -*- */
2/*
3 * MCI CDAUDIO Driver for OS/2. Interface to OS/2 DosIOCtrl()
4 *
5 * Copyright 2000 Chris Wohlgemuth
6 * 2001 Przemyslaw Dobrowolski
7 * Project Odin Software License can be found in LICENSE.TXT
8 *
9 */
10
11
12#define INCL_DOSDEVICES
13#define INCL_DOSDEVIOCTL
14#define INCL_DOS
15
16#include <os2wrap.h>
17#include <win32type.h>
18//#include <cdrom.h>
19
20#pragma pack(1)
21
22typedef struct{
23 UCHAR ucFirstTrack;
24 UCHAR ucLastTrack;
25 ULONG ulLeadOut;
26}CDINFO;
27
28typedef struct
29{
30 int ADR_data_for_track:4; // ADR data for track
31 int preemphasis:1; // 0 = Audio without preemphasis
32 // 1 = Audio with preemphasis
33 int cdda_permitted:1; // 0 = Digital copy prohibited
34 // 1 = Digital copy permitted
35 int type_of_track:1; // 0 = Audio track
36 // 1 = Data track
37 int channels:1; // 0 = Two-channel audio
38 // 1 = Four-channel audio
39}TRACKTYPE;
40
41typedef struct
42{
43 ULONG ulTrackAddress;
44 TRACKTYPE track_type;
45}CDTRACKINFO;
46
47typedef struct
48{
49 UCHAR signature[4];
50 UCHAR ucTrackNum;
51}TINFOPARAM;
52
53typedef struct
54{
55 UCHAR ucFrames;
56 UCHAR ucSeconds;
57 UCHAR ucMinutes;
58 UCHAR ucNotUsed;
59}MSF;
60
61typedef struct
62{
63 USHORT usStatusBits;
64 ULONG ulStarting;
65 ULONG ulEnding;
66}AUDIOSTATUS;
67
68typedef struct
69{
70 UCHAR signature[4];
71 UCHAR ucAddressMode;
72 ULONG ulStartSector;
73 ULONG ulEndSector;
74}PLAYPARAM2;
75
76typedef struct
77{
78 UCHAR signature[4];
79 UCHAR ucAddressMode;
80 ULONG ulTo;
81}SEEKPARAM;
82
83typedef struct
84{
85 UCHAR ucCtrlAdr;
86 UCHAR ucTrack;
87 UCHAR ucIndex;
88 UCHAR ucTrackMins;
89 UCHAR ucTrackSecs;
90 UCHAR UCTrackFrames;
91 UCHAR ucNull;
92 UCHAR ucDiskMins;
93 UCHAR ucDiskSecs;
94 UCHAR ucDiskFrames;
95}SUBCHANNELQ;
96
97#pragma pack()
98
99
100LONG static _CDCalculateSector(MSF* msf1)
101{
102 return ((msf1->ucMinutes*60+msf1->ucSeconds)*75+msf1->ucFrames);
103}
104
105
106HANDLE os2CDOpen(char *drive)
107{
108 HANDLE hfDrive = 0;
109 ULONG ulAction;
110 ULONG rc;
111
112 rc = DosOpen(drive, &hfDrive, &ulAction, 0,
113 FILE_NORMAL, OPEN_ACTION_OPEN_IF_EXISTS,
114 OPEN_SHARE_DENYNONE | OPEN_ACCESS_READONLY |
115 OPEN_FLAGS_DASD|OPEN_FLAGS_FAIL_ON_ERROR, NULL);
116
117 if(rc)
118 return 0;//Error
119
120 return hfDrive;
121}
122
123ULONG os2CDClose(ULONG hfOS2Handle)
124{
125 return DosClose(hfOS2Handle);
126}
127
128/******************************************/
129/* Result:
130 0: Error
131 -1: CD is Data Disk
132 other: # Audio tracks */
133/******************************************/
134int os2GetNumTracks(HANDLE hfOS2Handle, ULONG *ulLeadOut)
135{
136 ULONG ulParamLen;
137 ULONG ulDataLen;
138 ULONG rc;
139 CDINFO cdInfo;
140 TINFOPARAM tip;
141 CDTRACKINFO trackInfo;
142
143 ulDataLen=sizeof(cdInfo);
144 ulParamLen=4;
145
146 if(!hfOS2Handle)
147 return 0;
148
149 rc = DosDevIOCtl(hfOS2Handle, IOCTL_CDROMAUDIO, CDROMAUDIO_GETAUDIODISK,
150 (void*)"CD01", 4, &ulParamLen, &cdInfo,
151 sizeof(cdInfo), &ulDataLen);
152
153 if(rc) {
154 return 0;//Error
155 }
156
157 ulDataLen=sizeof(trackInfo);
158 ulParamLen=sizeof(TINFOPARAM);
159 tip.signature[0]='C';
160 tip.signature[1]='D';
161 tip.signature[2]='0';
162 tip.signature[3]='1';
163 tip.ucTrackNum=1;
164
165 /* We have a disc. Check if it's audio */
166 rc = DosDevIOCtl(hfOS2Handle, IOCTL_CDROMAUDIO, CDROMAUDIO_GETAUDIOTRACK,
167 &tip, sizeof(tip), &ulParamLen, &trackInfo,
168 sizeof(trackInfo), &ulDataLen);
169
170 if(rc) {
171 return 0;//Error
172 }
173
174// PD: Don't return error when data track is found.
175// if(trackInfo.ucTCInfo & 0x40) {
176// return -1;//It's a data track
177// }
178
179 *ulLeadOut=cdInfo.ulLeadOut;
180 return cdInfo.ucLastTrack-cdInfo.ucFirstTrack+1;
181}
182
183BOOL os2GetCDStatus(HANDLE hfOS2Handle, ULONG *ulStatus)
184{
185 ULONG ulParamLen;
186 ULONG ulDeviceStatus;
187 ULONG ulDataLen;
188 ULONG rc;
189
190 ulDeviceStatus=0;
191
192 /* Get status */
193 ulDataLen=sizeof(ulDeviceStatus);
194 ulParamLen=4;
195 rc = DosDevIOCtl(hfOS2Handle, IOCTL_CDROMDISK, CDROMDISK_DEVICESTATUS,
196 (void*)"CD01", 4, &ulParamLen, &ulDeviceStatus,
197 sizeof(ulDeviceStatus), &ulDataLen);
198 if(rc) {
199 return FALSE;//Error
200 }
201
202 *ulStatus=ulDeviceStatus;
203 return TRUE;
204}
205
206BOOL os2GetCDAudioStatus(HANDLE hfOS2Handle, USHORT *usStatus)
207{
208 AUDIOSTATUS asStatus;
209 ULONG ulParamLen;
210 ULONG ulDataLen;
211 ULONG rc;
212
213 /* Get status */
214
215 ulDataLen=sizeof(asStatus);
216 ulParamLen=4;
217
218 /* Get information */
219 rc = DosDevIOCtl(hfOS2Handle, IOCTL_CDROMAUDIO, CDROMAUDIO_GETAUDIOSTATUS,
220 (void*)"CD01", 4, &ulParamLen, &asStatus,
221 sizeof(asStatus), &ulDataLen);
222 if(rc) {
223 *usStatus=rc;
224 return FALSE;//Error
225 }
226 *usStatus=asStatus.usStatusBits;
227 return TRUE;
228}
229
230/* Returns sector info of track #numTrack */
231/* Starting with track 0 */
232ULONG os2CDQueryTrackStartSector( HANDLE hfDrive, ULONG numTrack, BOOL *pflAudio)
233{
234 ULONG ulParamLen;
235 ULONG ulDataLen;
236 ULONG rc;
237 CDINFO cdInfo;
238 TINFOPARAM tip;
239 CDTRACKINFO trackInfo[2];
240
241 do {
242 if(!hfDrive)
243 break;
244
245 /* Get cd info */
246 ulDataLen=sizeof(cdInfo);
247 ulParamLen=4;
248 rc = DosDevIOCtl(hfDrive, IOCTL_CDROMAUDIO, CDROMAUDIO_GETAUDIODISK,
249 (void*)"CD01", 4, &ulParamLen, &cdInfo,
250 sizeof(cdInfo), &ulDataLen);
251 if(rc)
252 break;//Error
253
254 ulDataLen=sizeof(trackInfo);
255 ulParamLen=sizeof(TINFOPARAM);
256 tip.signature[0]='C';
257 tip.signature[1]='D';
258 tip.signature[2]='0';
259 tip.signature[3]='1';
260 /* Get information about our track */
261 tip.ucTrackNum=numTrack+1;
262 if(tip.ucTrackNum<=cdInfo.ucLastTrack) {
263 rc = DosDevIOCtl(hfDrive, IOCTL_CDROMAUDIO, CDROMAUDIO_GETAUDIOTRACK,
264 &tip, sizeof(tip), &ulParamLen, &trackInfo[0],
265 sizeof(trackInfo[0]), &ulDataLen);
266 if(rc)
267 break;//Error
268
269 *pflAudio=!trackInfo[0].track_type.type_of_track;
270
271 }else
272 return _CDCalculateSector((MSF*)&cdInfo.ulLeadOut);
273
274
275 return _CDCalculateSector((MSF*)&trackInfo[0].ulTrackAddress);
276
277 }while(TRUE);
278
279 /* error */
280 return 0;
281}
282
283
284BOOL os2CDEject(HANDLE hfDrive)
285{
286 ULONG ulParamLen;
287 ULONG rc;
288
289 if(!hfDrive)
290 return FALSE;
291
292 ulParamLen=4;
293 rc = DosDevIOCtl(hfDrive, IOCTL_CDROMDISK, CDROMDISK_EJECTDISK,
294 (void*)"CD01", 4, &ulParamLen,0,
295 0, 0);
296 if(rc)
297 return FALSE;//Error
298
299 return TRUE;
300}
301
302#ifndef CDROMDISK_CLOSETRAY
303#define CDROMDISK_CLOSETRAY 0x0045
304#endif
305
306BOOL os2CDCloseTray(HANDLE hfDrive)
307{
308 ULONG ulParamLen;
309 ULONG rc;
310
311 if(!hfDrive)
312 return FALSE;
313
314 ulParamLen=4;
315 rc = DosDevIOCtl(hfDrive, IOCTL_CDROMDISK, CDROMDISK_CLOSETRAY,
316 (void*)"CD01", 4, &ulParamLen,0,
317 0, 0);
318 if(rc)
319 return FALSE;//Error
320
321 return TRUE;
322}
323
324BOOL os2CDStop(HANDLE hfDrive)
325{
326 ULONG ulParamLen;
327 ULONG rc;
328
329 if(!hfDrive)
330 return FALSE;
331
332
333
334 /* Stop CD */
335 ulParamLen=4;
336 rc = DosDevIOCtl(hfDrive, IOCTL_CDROMAUDIO, CDROMAUDIO_STOPAUDIO,
337 (void*)"CD01", 4, &ulParamLen,0,
338 0, 0);
339 if(rc)
340 return FALSE;//Error
341
342 return TRUE;
343}
344
345
346/*****************************************/
347/* */
348/* Plays frame range */
349/* */
350/* Returns TRUE if successful */
351/* */
352/*****************************************/
353BOOL os2CDPlayRange(HANDLE hfDrive ,ULONG ulFrom, ULONG ulTo)
354{
355 ULONG ulParamLen;
356 ULONG ulDataLen;
357 ULONG rc;
358 CDINFO cdInfo;
359 TINFOPARAM tip;
360 CDTRACKINFO trackInfo[2];
361 PLAYPARAM2 playParam={0};
362
363 if(!hfDrive)
364 return FALSE;
365
366 //memcpy(&playParam,PlayParam, sizeof(playParam));
367 /* Play the Track... */
368 ulParamLen=sizeof(PLAYPARAM2);
369 playParam.signature[0]='C';
370 playParam.signature[1]='D';
371 playParam.signature[2]='0';
372 playParam.signature[3]='1';
373 //playParam.ucAddressMode=01;
374 playParam.ulStartSector=ulFrom;
375 playParam.ulEndSector=ulTo;
376
377 rc = DosDevIOCtl(hfDrive, IOCTL_CDROMAUDIO, CDROMAUDIO_PLAYAUDIO,
378 &playParam, sizeof(playParam), &ulParamLen,0,
379 0, 0);
380 return rc;
381 if(rc)
382 return FALSE;
383
384 return TRUE;
385}
386
387BOOL os2CDResume(HANDLE hfDrive)
388{
389 ULONG ulParamLen;
390 ULONG rc;
391
392 if(!hfDrive)
393 return FALSE;
394
395 /* Stop CD */
396 ulParamLen=4;
397 rc = DosDevIOCtl(hfDrive, IOCTL_CDROMAUDIO, CDROMAUDIO_RESUMEAUDIO,
398 (void*)"CD01", 4, &ulParamLen,0,
399 0, 0);
400 if(rc)
401 return FALSE;//Error
402
403 return TRUE;
404}
405
406BOOL os2CDGetHeadLocation(HANDLE hfOS2Handle, ULONG *ulHeadLocation)
407{
408 UCHAR ucParam[5]={0};
409 ULONG ulParamLen;
410 ULONG ulDeviceStatus;
411 ULONG ulDataLen;
412 ULONG rc;
413
414 ulDeviceStatus=0;
415
416 if(!hfOS2Handle)
417 return FALSE;
418
419 /* Get Location */
420 ulDataLen=sizeof(ulDeviceStatus);
421 ulParamLen=5;
422 ucParam[0]='C';
423 ucParam[1]='D';
424 ucParam[2]='0';
425 ucParam[3]='1';
426 ucParam[4]=0;
427
428 rc = DosDevIOCtl(hfOS2Handle, IOCTL_CDROMDISK, CDROMDISK_GETHEADLOC,
429 &ucParam, 5, &ulParamLen, &ulDeviceStatus,
430 sizeof(ulDeviceStatus), &ulDataLen);
431 if(rc) {
432 return FALSE;//Error
433 }
434
435 *ulHeadLocation=ulDeviceStatus;
436 return TRUE;
437
438}
439
440BOOL os2CDSeek(HANDLE hfOS2Handle, ULONG ulTo)
441{
442 SEEKPARAM sp={0};
443 ULONG ulParamLen;
444 ULONG rc;
445
446 if(!hfOS2Handle)
447 return FALSE;
448
449 sp.signature[0]='C';
450 sp.signature[1]='D';
451 sp.signature[2]='0';
452 sp.signature[3]='1';
453 sp.ulTo=ulTo;
454
455 ulParamLen=sizeof(sp);
456
457 /* We have a disc. Check if it's audio */
458 rc = DosDevIOCtl(hfOS2Handle, IOCTL_CDROMDISK, CDROMDISK_SEEK,
459 &sp, sizeof(sp), &ulParamLen, 0,
460 0, 0);
461
462 if(rc) {
463 return FALSE;//Error
464 }
465
466 return TRUE;
467}
468
469BOOL os2CDQueryCurTrack(HANDLE hfOS2Handle, UINT * uiCurTrack)
470{
471 ULONG ulParamLen;
472 ULONG ulDeviceStatus;
473 ULONG ulDataLen;
474 ULONG rc;
475 SUBCHANNELQ scq;
476
477
478 if(!hfOS2Handle)
479 return FALSE;
480
481
482 /* Get status */
483 ulDataLen=sizeof(scq);
484 ulParamLen=4;
485 rc = DosDevIOCtl(hfOS2Handle, IOCTL_CDROMAUDIO, CDROMAUDIO_GETSUBCHANNELQ,
486 (void*)"CD01", 4, &ulParamLen, &scq,
487 sizeof(scq), &ulDataLen);
488 if(rc) {
489 return FALSE;//Error
490 }
491 *uiCurTrack=(scq.ucTrack & 0xF)+(scq.ucTrack & 0xF0)*10;
492 return TRUE;
493}
494
495/**************************************************************/
496/* */
497/* This funktion returns the CD-Drives in the system */
498/* */
499/* iNumCD (output): # of CD-Drives */
500/* cFirstDrive (output): first cd-Drive letter */
501/* returns TRUE: We have cd-drives */
502/* */
503/**************************************************************/
504BOOL os2CDQueryCDDrives(int *iNumCD, char * cFirstDrive)
505{
506 HANDLE hfDevice;
507 ULONG ulAction;
508 ULONG ulLen;
509 static char cFirst=0;
510 static int iNumCDLocal=0;
511 static BOOL haveCD=FALSE;
512 static BOOL done=FALSE;
513
514 struct
515 {
516 USHORT usCountCD;
517 USHORT usFirstCD;
518 } CDInfo;
519
520 if(!done){
521 ulLen = sizeof(CDInfo);
522 if(!DosOpen("\\DEV\\CD-ROM2$", &hfDevice, &ulAction, 0,
523 FILE_NORMAL, OPEN_ACTION_OPEN_IF_EXISTS,
524 OPEN_SHARE_DENYNONE | OPEN_ACCESS_READONLY, NULL))
525 {
526 if(!DosDevIOCtl(hfDevice, 0x82, 0x60, NULL, 0, NULL, &CDInfo, ulLen, &ulLen))
527 {
528 if(CDInfo.usCountCD) {
529 haveCD=TRUE;
530 iNumCDLocal=CDInfo.usCountCD;
531 cFirst='A'+ CDInfo.usFirstCD;
532 }
533 }
534 DosClose(hfDevice);
535 }
536 done=TRUE;
537 }
538 *iNumCD=iNumCDLocal;
539 *cFirstDrive=cFirst;
540 return haveCD;
541}
542
543
544
545
546
547
548
549
550
551
Note: See TracBrowser for help on using the repository browser.