1 /* $Id: rbaudio.c,v 1.8 2003/03/21 01:57:58 btb Exp $ */
2 /*
3  *
4  * SDL CD Audio functions
5  *
6  *
7  */
8 
9 #ifdef HAVE_CONFIG_H
10 #include <conf.h>
11 #endif
12 
13 #include <stdio.h>
14 #include <stdlib.h>
15 
16 #include <SDL.h>
17 
18 #ifdef __linux__
19 #include <sys/ioctl.h>
20 #include <linux/cdrom.h>
21 #endif
22 
23 #include "pstypes.h"
24 #include "error.h"
25 #include "args.h"
26 #include "rbaudio.h"
27 
28 static SDL_CD *s_cd = NULL;
29 static int initialised = 0;
30 
RBAExit()31 void RBAExit()
32 {
33 	if (initialised)
34 	{
35 		SDL_CDStop(s_cd);
36 		SDL_CDClose(s_cd);
37 	}
38 }
39 
RBAInit()40 void RBAInit()
41 {
42 	if (initialised) return;
43 	if (FindArg("-nocdrom")) return;
44 
45 	if (SDL_Init(SDL_INIT_CDROM) < 0)
46 	{
47 		Warning("SDL library initialisation failed: %s.",SDL_GetError());
48 		return;
49 	}
50 
51 	if (SDL_CDNumDrives() == 0)
52 	{
53 		Warning("No cdrom drives found!\n");
54 		return;
55 	}
56 	s_cd = SDL_CDOpen(0);
57 	if (s_cd == NULL) {
58 		Warning("Could not open cdrom for redbook audio!\n");
59 		return;
60 	}
61 	atexit(RBAExit);
62 	initialised = 1;
63 }
64 
RBAEnabled()65 int RBAEnabled()
66 {
67 	return 1;
68 }
69 
RBARegisterCD()70 void RBARegisterCD()
71 {
72 
73 }
74 
RBAPlayTrack(int a)75 int RBAPlayTrack(int a)
76 {
77 	if (!initialised) return -1;
78 
79 	if (CD_INDRIVE(SDL_CDStatus(s_cd)) ) {
80 		SDL_CDPlayTracks(s_cd, a-1, 0, 0, 0);
81 	}
82 	return a;
83 }
84 
RBAStop()85 void RBAStop()
86 {
87 	if (!initialised) return;
88 	SDL_CDStop(s_cd);
89 }
90 
RBASetVolume(int volume)91 void RBASetVolume(int volume)
92 {
93 #ifdef __linux__
94 	int cdfile, level;
95 	struct cdrom_volctrl volctrl;
96 
97 	if (!initialised) return;
98 
99 	cdfile = s_cd->id;
100 	level = volume * 3;
101 
102 	if ((level<0) || (level>255)) {
103 		fprintf(stderr, "illegal volume value (allowed values 0-255)\n");
104 		return;
105 	}
106 
107 	volctrl.channel0
108 		= volctrl.channel1
109 		= volctrl.channel2
110 		= volctrl.channel3
111 		= level;
112 	if ( ioctl(cdfile, CDROMVOLCTRL, &volctrl) == -1 ) {
113 		fprintf(stderr, "CDROMVOLCTRL ioctl failed\n");
114 		return;
115 	}
116 #endif
117 }
118 
RBAPause()119 void RBAPause()
120 {
121 	if (!initialised) return;
122 	SDL_CDPause(s_cd);
123 }
124 
RBAResume()125 int RBAResume()
126 {
127 	if (!initialised) return -1;
128 	SDL_CDResume(s_cd);
129 	return 1;
130 }
131 
RBAGetNumberOfTracks()132 int RBAGetNumberOfTracks()
133 {
134 	if (!initialised) return -1;
135 	SDL_CDStatus(s_cd);
136 	return s_cd->numtracks;
137 }
138 
RBAPlayTracks(int tracknum,int something)139 int RBAPlayTracks(int tracknum,int something)
140 {
141 	if (!initialised) return -1;
142 	if (CD_INDRIVE(SDL_CDStatus(s_cd)) ) {
143 		SDL_CDPlayTracks(s_cd, tracknum-1, 0, 0, 0);
144 	}
145 	return tracknum;
146 }
147 
RBAGetTrackNum()148 int RBAGetTrackNum()
149 {
150 	if (!initialised) return -1;
151 	SDL_CDStatus(s_cd);
152 	return s_cd->cur_track;
153 }
154 
RBAPeekPlayStatus()155 int RBAPeekPlayStatus()
156 {
157 	return (SDL_CDStatus(s_cd) == CD_PLAYING);
158 }
159 
CD_blast_mixer()160 int CD_blast_mixer()
161 {
162 	return 0;
163 }
164 
165 
cddb_sum(int n)166 static int cddb_sum(int n)
167 {
168 	int ret;
169 
170 	/* For backward compatibility this algorithm must not change */
171 
172 	ret = 0;
173 
174 	while (n > 0) {
175 		ret = ret + (n % 10);
176 		n = n / 10;
177 	}
178 
179 	return (ret);
180 }
181 
182 
RBAGetDiscID()183 unsigned long RBAGetDiscID()
184 {
185 	int i, t = 0, n = 0;
186 
187 	if (!initialised)
188 		return 0;
189 
190 	/* For backward compatibility this algorithm must not change */
191 
192 	i = 0;
193 
194 	while (i < s_cd->numtracks) {
195 		n += cddb_sum(s_cd->track[i].offset / CD_FPS);
196 		i++;
197 	}
198 
199 	t = (s_cd->track[s_cd->numtracks].offset / CD_FPS) -
200 	    (s_cd->track[0].offset / CD_FPS);
201 
202 	return ((n % 0xff) << 24 | t << 8 | s_cd->numtracks);
203 }
204