comparison src/xs_sidplay2.cc @ 73:2bc607888f53

Added libsidplay2 module, lots of reworking of internals, sidplay1 support now works with the new framework! Getting libsidplay2 support working shouldn't be too far now...
author Matti Hamalainen <ccr@tnsp.org>
date Sun, 14 Sep 2003 03:14:01 +0000
parents
children 8cb66a3f75f7
comparison
equal deleted inserted replaced
72:e3b205a6bc7e 73:2bc607888f53
1 /*
2 XMMS-SID - SIDPlay input plugin for X MultiMedia System (XMMS)
3
4 libSIDPlay v2 support
5
6 Written by Matti "ccr" Hamalainen <ccr@tnsp.org>
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
21 */
22 #include "xmms-sid.h"
23
24 #ifdef HAVE_SIDPLAY2
25
26 extern "C" {
27 #include "xs_sidplay2.h"
28 #include <stdio.h>
29 #include <xmms/titlestring.h>
30 #include "xs_config.h"
31 #include "xs_support.h"
32 #include "xs_length.h"
33 }
34
35 #include <sidplay/sidplay2.h>
36 #ifdef HAVE_RESID_BUILDER
37 #include <sidplay/builders/resid.h>
38 #endif
39 #ifdef HAVE_HARDSID_BUILDER
40 /* Dummy now */
41 #endif
42
43
44 typedef struct {
45 sidplay2 *currEng;
46 sid2_config_t currConfig;
47 SidTune *currTune;
48 } t_xs_sidplay2;
49
50
51 /*
52 * We need to 'export' all this pseudo-C++ crap
53 */
54 extern "C" {
55
56 gboolean xs_sidplay2_isourfile(gchar *pcFileName)
57 {
58 /* Try to detect via libSIDPlay's detection routine, if required */
59 SidTune *testTune = new SidTune(pcFileName);
60
61 if (!testTune) return FALSE;
62 if (!testTune->getStatus())
63 {
64 delete testTune;
65 return FALSE;
66 }
67
68 delete testTune;
69 return TRUE;
70 }
71
72
73 void xs_sidplay2_close(t_xs_status *myStatus)
74 {
75 t_xs_sidplay2 *myPlayer;
76 sidbuilder *myBuilder;
77
78 /* Check pointer */
79 if (!myStatus) return;
80
81 /* Free internals */
82 myPlayer = (t_xs_sidplay2 *) myStatus->player;
83
84 myBuilder = myPlayer->currConfig.sidEmulation;
85 myPlayer->currEng->config(myPlayer->currConfig);
86
87 delete myBuilder;
88 delete myPlayer->currEng;
89
90 xs_sidplay2_deletesid(myStatus);
91
92 free(myPlayer);
93 myStatus->player = NULL;
94
95 /* Miscellaneous */
96 free(myStatus->currFileName);
97 myStatus->currFileName = NULL;
98 }
99
100
101 gboolean xs_sidplay2_init(t_xs_status *myStatus)
102 {
103 t_xs_sidplay2 *myPlayer;
104
105 /* Check pointer */
106 if (!myStatus) return FALSE;
107
108 /* Allocate internal structures */
109 myPlayer = (t_xs_sidplay2 *) g_malloc0(sizeof(t_xs_sidplay2));
110 if (!myPlayer) return FALSE;
111
112 /* Initialize engine */
113 myPlayer->currEng = new sidplay2;
114 if (!myPlayer->currEng)
115 {
116 XSERR("Could not initialize libSIDPlay2 emulation engine\n");
117 free(myPlayer);
118 return FALSE;
119 }
120
121 myStatus->player = myPlayer;
122 return TRUE;
123 }
124
125
126 gboolean xs_sidplay2_initsong(t_xs_status *myStatus)
127 {
128 t_xs_sidplay2 *myPlayer = (t_xs_sidplay2 *) myStatus->player;
129
130 if (!myPlayer || !myPlayer->currTune) return FALSE;
131
132 myPlayer->currTune->selectSong(myStatus->currSong);
133
134 return myPlayer->currEng->load(myPlayer->currTune);
135 }
136
137
138 gboolean xs_sidplay2_fillbuffer(t_xs_status *myStatus, gchar *audioBuffer, gint audioBufSize)
139 {
140 t_xs_sidplay2 *myPlayer = (t_xs_sidplay2 *) myStatus->player;
141
142 if (!myPlayer) return FALSE;
143
144 return (myPlayer->currEng->play(audioBuffer, audioBufSize) == audioBufSize);
145 }
146
147
148 gboolean xs_sidplay2_loadsid(t_xs_status *myStatus, gchar *pcFileName)
149 {
150 t_xs_sidplay2 *myPlayer = (t_xs_sidplay2 *) myStatus->player;
151 SidTune *newTune;
152 SidTuneInfo tuneInfo;
153
154 /* Try to get the tune */
155 if (!pcFileName) return FALSE;
156 newTune = new SidTune(pcFileName);
157 if (!newTune) return FALSE;
158
159 /* Get current configuration */
160 myPlayer->currEng->getConfig(myPlayer->currConfig);
161
162 /* Configure channels and stuff */
163 switch (xs_cfg.fmtChannels) {
164
165 case XS_CHN_AUTOPAN:
166 myPlayer->currConfig.channels = SIDEMU_STEREO;
167 myPlayer->currConfig.autoPanning = SIDEMU_CENTEREDAUTOPANNING;
168 myPlayer->currConfig.volumeControl = SIDEMU_FULLPANNING;
169 break;
170
171 case XS_CHN_STEREO:
172 myPlayer->currConfig.channels = SIDEMU_STEREO;
173 myPlayer->currConfig.autoPanning = SIDEMU_NONE;
174 myPlayer->currConfig.volumeControl = SIDEMU_NONE;
175 break;
176
177 case XS_CHN_MONO:
178 default:
179 myPlayer->currConfig.channels = SIDEMU_MONO;
180 myPlayer->currConfig.autoPanning = SIDEMU_NONE;
181 myPlayer->currConfig.volumeControl = SIDEMU_NONE;
182 break;
183 }
184
185
186 /* Memory mode settings */
187 switch (xs_cfg.memoryMode) {
188 case XS_MPU_BANK_SWITCHING:
189 myPlayer->currConfig.memoryMode = MPU_BANK_SWITCHING;
190 break;
191
192 case XS_MPU_TRANSPARENT_ROM:
193 myPlayer->currConfig.memoryMode = MPU_TRANSPARENT_ROM;
194 break;
195
196 case XS_MPU_PLAYSID_ENVIRONMENT:
197 myPlayer->currConfig.memoryMode = MPU_PLAYSID_ENVIRONMENT;
198 break;
199
200 default:
201 myPlayer->currConfig.memoryMode = MPU_BANK_SWITCHING;
202 break;
203 }
204
205
206 /* Clockspeed settings */
207 switch (xs_cfg.clockSpeed) {
208 case XS_CLOCK_NTSC:
209 myPlayer->currConfig.clockSpeed = SIDTUNE_CLOCK_NTSC;
210 break;
211
212 case XS_CLOCK_PAL:
213 default:
214 myPlayer->currConfig.clockSpeed = SIDTUNE_CLOCK_PAL;
215 break;
216 }
217
218
219 /* Configure rest of the emulation */
220 myPlayer->currConfig.bitsPerSample = xs_cfg.fmtBitsPerSample;
221 myPlayer->currConfig.frequency = xs_cfg.fmtFrequency;
222 #ifdef HAVE_UNSIGNEDPCM
223 myPlayer->currConfig.sampleFormat = SIDEMU_UNSIGNED_PCM;
224 #else
225 myPlayer->currConfig.sampleFormat = SIDEMU_SIGNED_PCM;
226 #endif
227 myPlayer->currConfig.mos8580 = xs_cfg.mos8580;
228 myPlayer->currConfig.emulateFilter = xs_cfg.emulateFilters;
229 myPlayer->currConfig.filterFs = xs_cfg.filterFs;
230 myPlayer->currConfig.filterFm = xs_cfg.filterFm;
231 myPlayer->currConfig.filterFt = xs_cfg.filterFt;
232
233 /* Now set the emulator configuration */
234 myPlayer->currEng->setConfig(myPlayer->currConfig);
235
236 /* Initialize status information */
237 newTune->getInfo(tuneInfo);
238
239 myStatus->isPlaying = TRUE;
240 myStatus->isError = FALSE;
241 myStatus->currSong = tuneInfo.startSong;
242 myStatus->nSongs = tuneInfo.songs;
243 myPlayer->currTune = newTune;
244 myStatus->currFileName = g_strdup(pcFileName);
245
246 return TRUE;
247 }
248
249
250 /*
251 * Delete tune
252 */
253 void xs_sidplay2_deletesid(t_xs_status *myStatus)
254 {
255 t_xs_sidplay2 *myPlayer;
256
257 if (!myStatus) return;
258
259 myPlayer = (t_xs_sidplay2 *) myStatus->player;
260 if (!myPlayer) return;
261
262 if (myPlayer->currTune)
263 delete myPlayer->currTune;
264 }
265
266
267 gint xs_sidplay2_gettunespeed(t_xs_status *myStatus)
268 {
269 return 0;
270 }
271
272 /*
273 * Return song information
274 */
275 void xs_sidplay2_getsidinfo(gchar *songFileName, gchar **songTitle, gint *songLength)
276 {
277 }
278
279
280 } /* extern "C" */
281 #endif /* HAVE_SIDPLAY2 */