~vcs-imports/qemu/git

« back to all changes in this revision

Viewing changes to audio/audio.c

  • Committer: bellard
  • Date: 2004-11-07 18:04:02 UTC
  • Revision ID: git-v1:85571bc7415c3fa9390f5edc3720ec7975219a68
audio merge (malc)


git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@1125 c046a42c-6fe2-441c-8c8c-71466251a162

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * QEMU Audio subsystem
 
3
 * 
 
4
 * Copyright (c) 2003-2004 Vassili Karpov (malc)
 
5
 * 
 
6
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 
7
 * of this software and associated documentation files (the "Software"), to deal
 
8
 * in the Software without restriction, including without limitation the rights
 
9
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 
10
 * copies of the Software, and to permit persons to whom the Software is
 
11
 * furnished to do so, subject to the following conditions:
 
12
 *
 
13
 * The above copyright notice and this permission notice shall be included in
 
14
 * all copies or substantial portions of the Software.
 
15
 *
 
16
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 
17
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 
18
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
 
19
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 
20
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 
21
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 
22
 * THE SOFTWARE.
 
23
 */
 
24
#include <assert.h>
 
25
#include <limits.h>
 
26
#include "vl.h"
 
27
 
 
28
#define AUDIO_CAP "audio"
 
29
#include "audio/audio.h"
 
30
 
 
31
#define USE_SDL_AUDIO
 
32
#define USE_WAV_AUDIO
 
33
 
 
34
#if defined __linux__ || (defined _BSD && !defined __APPLE__)
 
35
#define USE_OSS_AUDIO
 
36
#endif
 
37
 
 
38
#ifdef USE_OSS_AUDIO
 
39
#include "audio/ossaudio.h"
 
40
#endif
 
41
 
 
42
#ifdef USE_SDL_AUDIO
 
43
#include "audio/sdlaudio.h"
 
44
#endif
 
45
 
 
46
#ifdef USE_WAV_AUDIO
 
47
#include "audio/wavaudio.h"
 
48
#endif
 
49
 
 
50
#ifdef USE_FMOD_AUDIO
 
51
#include "audio/fmodaudio.h"
 
52
#endif
 
53
 
 
54
#define QC_AUDIO_DRV    "QEMU_AUDIO_DRV"
 
55
#define QC_VOICES    "QEMU_VOICES"
 
56
#define QC_FIXED_FORMAT "QEMU_FIXED_FORMAT"
 
57
#define QC_FIXED_FREQ   "QEMU_FIXED_FREQ"
 
58
 
 
59
extern void SB16_init (void);
 
60
 
 
61
#ifdef USE_ADLIB
 
62
extern void Adlib_init (void);
 
63
#endif
 
64
 
 
65
#ifdef USE_GUS
 
66
extern void GUS_init (void);
 
67
#endif
 
68
 
 
69
static void (*hw_ctors[]) (void) = {
 
70
    SB16_init,
 
71
#ifdef USE_ADLIB
 
72
    Adlib_init,
 
73
#endif
 
74
#ifdef USE_GUS
 
75
    GUS_init,
 
76
#endif
 
77
    NULL
 
78
};
 
79
 
 
80
static HWVoice *hw_voice;
 
81
 
 
82
AudioState audio_state = {
 
83
    1,                          /* use fixed settings */
 
84
    44100,                      /* fixed frequency */
 
85
    2,                          /* fixed channels */
 
86
    AUD_FMT_S16,                /* fixed format */
 
87
    1,                          /* number of hw voices */
 
88
    -1                          /* voice size */
 
89
};
 
90
 
 
91
/* http://www.df.lth.se/~john_e/gems/gem002d.html */
 
92
/* http://www.multi-platforms.com/Tips/PopCount.htm */
 
93
uint32_t popcount (uint32_t u)
 
94
{
 
95
    u = ((u&0x55555555) + ((u>>1)&0x55555555));
 
96
    u = ((u&0x33333333) + ((u>>2)&0x33333333));
 
97
    u = ((u&0x0f0f0f0f) + ((u>>4)&0x0f0f0f0f));
 
98
    u = ((u&0x00ff00ff) + ((u>>8)&0x00ff00ff));
 
99
    u = ( u&0x0000ffff) + (u>>16);
 
100
    return u;
 
101
}
 
102
 
 
103
inline uint32_t lsbindex (uint32_t u)
 
104
{
 
105
    return popcount ((u&-u)-1);
 
106
}
 
107
 
 
108
int audio_get_conf_int (const char *key, int defval)
 
109
{
 
110
    int val = defval;
 
111
    char *strval;
 
112
 
 
113
    strval = getenv (key);
 
114
    if (strval) {
 
115
        val = atoi (strval);
 
116
    }
 
117
 
 
118
    return val;
 
119
}
 
120
 
 
121
const char *audio_get_conf_str (const char *key, const char *defval)
 
122
{
 
123
    const char *val = getenv (key);
 
124
    if (!val)
 
125
        return defval;
 
126
    else
 
127
        return val;
 
128
}
 
129
 
 
130
void audio_log (const char *fmt, ...)
 
131
{
 
132
    va_list ap;
 
133
    va_start (ap, fmt);
 
134
    vfprintf (stderr, fmt, ap);
 
135
    va_end (ap);
 
136
}
 
137
 
 
138
/*
 
139
 * Soft Voice
 
140
 */
 
141
void pcm_sw_free_resources (SWVoice *sw)
 
142
{
 
143
    if (sw->buf) qemu_free (sw->buf);
 
144
    if (sw->rate) st_rate_stop (sw->rate);
 
145
    sw->buf = NULL;
 
146
    sw->rate = NULL;
 
147
}
 
148
 
 
149
int pcm_sw_alloc_resources (SWVoice *sw)
 
150
{
 
151
    sw->buf = qemu_mallocz (sw->hw->samples * sizeof (st_sample_t));
 
152
    if (!sw->buf)
 
153
        return -1;
 
154
 
 
155
    sw->rate = st_rate_start (sw->freq, sw->hw->freq);
 
156
    if (!sw->rate) {
 
157
        qemu_free (sw->buf);
 
158
        sw->buf = NULL;
 
159
        return -1;
 
160
    }
 
161
    return 0;
 
162
}
 
163
 
 
164
void pcm_sw_fini (SWVoice *sw)
 
165
{
 
166
    pcm_sw_free_resources (sw);
 
167
}
 
168
 
 
169
int pcm_sw_init (SWVoice *sw, HWVoice *hw, int freq,
 
170
                 int nchannels, audfmt_e fmt)
 
171
{
 
172
    int bits = 8, sign = 0;
 
173
 
 
174
    switch (fmt) {
 
175
    case AUD_FMT_S8:
 
176
        sign = 1;
 
177
    case AUD_FMT_U8:
 
178
        break;
 
179
 
 
180
    case AUD_FMT_S16:
 
181
        sign = 1;
 
182
    case AUD_FMT_U16:
 
183
        bits = 16;
 
184
        break;
 
185
    }
 
186
 
 
187
    sw->hw = hw;
 
188
    sw->freq = freq;
 
189
    sw->fmt = fmt;
 
190
    sw->nchannels = nchannels;
 
191
    sw->shift = (nchannels == 2) + (bits == 16);
 
192
    sw->align = (1 << sw->shift) - 1;
 
193
    sw->left = 0;
 
194
    sw->pos = 0;
 
195
    sw->wpos = 0;
 
196
    sw->live = 0;
 
197
    sw->ratio = (sw->hw->freq * ((int64_t) INT_MAX)) / sw->freq;
 
198
    sw->bytes_per_second = sw->freq << sw->shift;
 
199
    sw->conv = mixeng_conv[nchannels == 2][sign][bits == 16];
 
200
 
 
201
    pcm_sw_free_resources (sw);
 
202
    return pcm_sw_alloc_resources (sw);
 
203
}
 
204
 
 
205
/* Hard voice */
 
206
void pcm_hw_free_resources (HWVoice *hw)
 
207
{
 
208
    if (hw->mix_buf)
 
209
        qemu_free (hw->mix_buf);
 
210
    hw->mix_buf = NULL;
 
211
}
 
212
 
 
213
int pcm_hw_alloc_resources (HWVoice *hw)
 
214
{
 
215
    hw->mix_buf = qemu_mallocz (hw->samples * sizeof (st_sample_t));
 
216
    if (!hw->mix_buf)
 
217
        return -1;
 
218
    return 0;
 
219
}
 
220
 
 
221
 
 
222
void pcm_hw_fini (HWVoice *hw)
 
223
{
 
224
    if (hw->active) {
 
225
        ldebug ("pcm_hw_fini: %d %d %d\n", hw->freq, hw->nchannels, hw->fmt);
 
226
        pcm_hw_free_resources (hw);
 
227
        hw->pcm_ops->fini (hw);
 
228
        memset (hw, 0, audio_state.drv->voice_size);
 
229
    }
 
230
}
 
231
 
 
232
void pcm_hw_gc (HWVoice *hw)
 
233
{
 
234
    if (hw->nb_voices)
 
235
        return;
 
236
 
 
237
    pcm_hw_fini (hw);
 
238
}
 
239
 
 
240
int pcm_hw_get_live (HWVoice *hw)
 
241
{
 
242
    int i, alive = 0, live = hw->samples;
 
243
 
 
244
    for (i = 0; i < hw->nb_voices; i++) {
 
245
        if (hw->pvoice[i]->live) {
 
246
            live = audio_MIN (hw->pvoice[i]->live, live);
 
247
            alive += 1;
 
248
        }
 
249
    }
 
250
 
 
251
    if (alive)
 
252
        return live;
 
253
    else
 
254
        return -1;
 
255
}
 
256
 
 
257
int pcm_hw_get_live2 (HWVoice *hw, int *nb_active)
 
258
{
 
259
    int i, alive = 0, live = hw->samples;
 
260
 
 
261
    *nb_active = 0;
 
262
    for (i = 0; i < hw->nb_voices; i++) {
 
263
        if (hw->pvoice[i]->live) {
 
264
            if (hw->pvoice[i]->live < live) {
 
265
                *nb_active = hw->pvoice[i]->active != 0;
 
266
                live = hw->pvoice[i]->live;
 
267
            }
 
268
            alive += 1;
 
269
        }
 
270
    }
 
271
 
 
272
    if (alive)
 
273
        return live;
 
274
    else
 
275
        return -1;
 
276
}
 
277
 
 
278
void pcm_hw_dec_live (HWVoice *hw, int decr)
 
279
{
 
280
    int i;
 
281
 
 
282
    for (i = 0; i < hw->nb_voices; i++) {
 
283
        if (hw->pvoice[i]->live) {
 
284
            hw->pvoice[i]->live -= decr;
 
285
        }
 
286
    }
 
287
}
 
288
 
 
289
void pcm_hw_clear (HWVoice *hw, void *buf, int len)
 
290
{
 
291
    if (!len)
 
292
        return;
 
293
 
 
294
    switch (hw->fmt) {
 
295
    case AUD_FMT_S16:
 
296
    case AUD_FMT_S8:
 
297
        memset (buf, len << hw->shift, 0x00);
 
298
        break;
 
299
 
 
300
    case AUD_FMT_U8:
 
301
        memset (buf, len << hw->shift, 0x80);
 
302
        break;
 
303
 
 
304
    case AUD_FMT_U16:
 
305
        {
 
306
            unsigned int i;
 
307
            uint16_t *p = buf;
 
308
            int shift = hw->nchannels - 1;
 
309
 
 
310
            for (i = 0; i < len << shift; i++) {
 
311
                p[i] = INT16_MAX;
 
312
            }
 
313
        }
 
314
        break;
 
315
    }
 
316
}
 
317
 
 
318
int pcm_hw_write (SWVoice *sw, void *buf, int size)
 
319
{
 
320
    int hwsamples, samples, isamp, osamp, wpos, live, dead, left, swlim, blck;
 
321
    int ret = 0, pos = 0;
 
322
    if (!sw)
 
323
        return size;
 
324
 
 
325
    hwsamples = sw->hw->samples;
 
326
    samples = size >> sw->shift;
 
327
 
 
328
    if (!sw->live) {
 
329
        sw->wpos = sw->hw->rpos;
 
330
    }
 
331
    wpos = sw->wpos;
 
332
    live = sw->live;
 
333
    dead = hwsamples - live;
 
334
    swlim = (dead * ((int64_t) INT_MAX)) / sw->ratio;
 
335
    swlim = audio_MIN (swlim, samples);
 
336
 
 
337
    ldebug ("size=%d live=%d dead=%d swlim=%d wpos=%d\n",
 
338
           size, live, dead, swlim, wpos);
 
339
    if (swlim)
 
340
        sw->conv (sw->buf, buf, swlim);
 
341
 
 
342
    while (swlim) {
 
343
        dead = hwsamples - live;
 
344
        left = hwsamples - wpos;
 
345
        blck = audio_MIN (dead, left);
 
346
        if (!blck) {
 
347
            /* dolog ("swlim=%d\n", swlim); */
 
348
            break;
 
349
        }
 
350
        isamp = swlim;
 
351
        osamp = blck;
 
352
        st_rate_flow (sw->rate, sw->buf + pos, sw->hw->mix_buf + wpos, &isamp, &osamp);
 
353
        ret += isamp;
 
354
        swlim -= isamp;
 
355
        pos += isamp;
 
356
        live += osamp;
 
357
        wpos = (wpos + osamp) % hwsamples;
 
358
    }
 
359
 
 
360
    sw->wpos = wpos;
 
361
    sw->live = live;
 
362
    return ret << sw->shift;
 
363
}
 
364
 
 
365
int pcm_hw_init (HWVoice *hw, int freq, int nchannels, audfmt_e fmt)
 
366
{
 
367
    int sign = 0, bits = 8;
 
368
 
 
369
    pcm_hw_fini (hw);
 
370
    ldebug ("pcm_hw_init: %d %d %d\n", freq, nchannels, fmt);
 
371
    if (hw->pcm_ops->init (hw, freq, nchannels, fmt)) {
 
372
        memset (hw, 0, audio_state.drv->voice_size);
 
373
        return -1;
 
374
    }
 
375
 
 
376
    switch (hw->fmt) {
 
377
    case AUD_FMT_S8:
 
378
        sign = 1;
 
379
    case AUD_FMT_U8:
 
380
        break;
 
381
 
 
382
    case AUD_FMT_S16:
 
383
        sign = 1;
 
384
    case AUD_FMT_U16:
 
385
        bits = 16;
 
386
        break;
 
387
    }
 
388
 
 
389
    hw->nb_voices = 0;
 
390
    hw->active = 1;
 
391
    hw->shift = (hw->nchannels == 2) + (bits == 16);
 
392
    hw->bytes_per_second = hw->freq << hw->shift;
 
393
    hw->align = (1 << hw->shift) - 1;
 
394
    hw->samples = hw->bufsize >> hw->shift;
 
395
    hw->clip = mixeng_clip[hw->nchannels == 2][sign][bits == 16];
 
396
    if (pcm_hw_alloc_resources (hw)) {
 
397
        pcm_hw_fini (hw);
 
398
        return -1;
 
399
    }
 
400
    return 0;
 
401
}
 
402
 
 
403
static int dist (void *hw)
 
404
{
 
405
    if (hw) {
 
406
        return (((uint8_t *) hw - (uint8_t *) hw_voice)
 
407
                / audio_state.voice_size) + 1;
 
408
    }
 
409
    else {
 
410
        return 0;
 
411
    }
 
412
}
 
413
 
 
414
#define ADVANCE(hw) hw ? advance (hw, audio_state.voice_size) : hw_voice
 
415
 
 
416
HWVoice *pcm_hw_find_any (HWVoice *hw)
 
417
{
 
418
    int i = dist (hw);
 
419
    for (; i < audio_state.nb_hw_voices; i++) {
 
420
        hw = ADVANCE (hw);
 
421
        return hw;
 
422
    }
 
423
    return NULL;
 
424
}
 
425
 
 
426
HWVoice *pcm_hw_find_any_active (HWVoice *hw)
 
427
{
 
428
    int i = dist (hw);
 
429
    for (; i < audio_state.nb_hw_voices; i++) {
 
430
        hw = ADVANCE (hw);
 
431
        if (hw->active)
 
432
            return hw;
 
433
    }
 
434
    return NULL;
 
435
}
 
436
 
 
437
HWVoice *pcm_hw_find_any_active_enabled (HWVoice *hw)
 
438
{
 
439
    int i = dist (hw);
 
440
    for (; i < audio_state.nb_hw_voices; i++) {
 
441
        hw = ADVANCE (hw);
 
442
        if (hw->active && hw->enabled)
 
443
            return hw;
 
444
    }
 
445
    return NULL;
 
446
}
 
447
 
 
448
HWVoice *pcm_hw_find_any_passive (HWVoice *hw)
 
449
{
 
450
    int i = dist (hw);
 
451
    for (; i < audio_state.nb_hw_voices; i++) {
 
452
        hw = ADVANCE (hw);
 
453
        if (!hw->active)
 
454
            return hw;
 
455
    }
 
456
    return NULL;
 
457
}
 
458
 
 
459
HWVoice *pcm_hw_find_specific (HWVoice *hw, int freq,
 
460
                               int nchannels, audfmt_e fmt)
 
461
{
 
462
    while ((hw = pcm_hw_find_any_active (hw))) {
 
463
        if (hw->freq == freq &&
 
464
            hw->nchannels == nchannels &&
 
465
            hw->fmt == fmt)
 
466
            return hw;
 
467
    }
 
468
    return NULL;
 
469
}
 
470
 
 
471
HWVoice *pcm_hw_add (int freq, int nchannels, audfmt_e fmt)
 
472
{
 
473
    HWVoice *hw;
 
474
 
 
475
    if (audio_state.fixed_format) {
 
476
        freq = audio_state.fixed_freq;
 
477
        nchannels = audio_state.fixed_channels;
 
478
        fmt = audio_state.fixed_fmt;
 
479
    }
 
480
 
 
481
    hw = pcm_hw_find_specific (NULL, freq, nchannels, fmt);
 
482
 
 
483
    if (hw)
 
484
        return hw;
 
485
 
 
486
    hw = pcm_hw_find_any_passive (NULL);
 
487
    if (hw) {
 
488
        hw->pcm_ops = audio_state.drv->pcm_ops;
 
489
        if (!hw->pcm_ops)
 
490
            return NULL;
 
491
 
 
492
        if (pcm_hw_init (hw, freq, nchannels, fmt)) {
 
493
            pcm_hw_gc (hw);
 
494
            return NULL;
 
495
        }
 
496
        else
 
497
            return hw;
 
498
    }
 
499
 
 
500
    return pcm_hw_find_any (NULL);
 
501
}
 
502
 
 
503
int pcm_hw_add_sw (HWVoice *hw, SWVoice *sw)
 
504
{
 
505
    SWVoice **pvoice = qemu_mallocz ((hw->nb_voices + 1) * sizeof (sw));
 
506
    if (!pvoice)
 
507
        return -1;
 
508
 
 
509
    memcpy (pvoice, hw->pvoice, hw->nb_voices * sizeof (sw));
 
510
    qemu_free (hw->pvoice);
 
511
    hw->pvoice = pvoice;
 
512
    hw->pvoice[hw->nb_voices++] = sw;
 
513
    return 0;
 
514
}
 
515
 
 
516
int pcm_hw_del_sw (HWVoice *hw, SWVoice *sw)
 
517
{
 
518
    int i, j;
 
519
    if (hw->nb_voices > 1) {
 
520
        SWVoice **pvoice = qemu_mallocz ((hw->nb_voices - 1) * sizeof (sw));
 
521
 
 
522
        if (!pvoice) {
 
523
            dolog ("Can not maintain consistent state (not enough memory)\n");
 
524
            return -1;
 
525
        }
 
526
 
 
527
        for (i = 0, j = 0; i < hw->nb_voices; i++) {
 
528
            if (j >= hw->nb_voices - 1) {
 
529
                dolog ("Can not maintain consistent state "
 
530
                       "(invariant violated)\n");
 
531
                return -1;
 
532
            }
 
533
            if (hw->pvoice[i] != sw)
 
534
                pvoice[j++] = hw->pvoice[i];
 
535
        }
 
536
        qemu_free (hw->pvoice);
 
537
        hw->pvoice = pvoice;
 
538
        hw->nb_voices -= 1;
 
539
    }
 
540
    else {
 
541
        qemu_free (hw->pvoice);
 
542
        hw->pvoice = NULL;
 
543
        hw->nb_voices = 0;
 
544
    }
 
545
    return 0;
 
546
}
 
547
 
 
548
SWVoice *pcm_create_voice_pair (int freq, int nchannels, audfmt_e fmt)
 
549
{
 
550
    SWVoice *sw;
 
551
    HWVoice *hw;
 
552
 
 
553
    sw = qemu_mallocz (sizeof (*sw));
 
554
    if (!sw)
 
555
        goto err1;
 
556
 
 
557
    hw = pcm_hw_add (freq, nchannels, fmt);
 
558
    if (!hw)
 
559
        goto err2;
 
560
 
 
561
    if (pcm_hw_add_sw (hw, sw))
 
562
        goto err3;
 
563
 
 
564
    if (pcm_sw_init (sw, hw, freq, nchannels, fmt))
 
565
        goto err4;
 
566
 
 
567
    return sw;
 
568
 
 
569
err4:
 
570
    pcm_hw_del_sw (hw, sw);
 
571
err3:
 
572
    pcm_hw_gc (hw);
 
573
err2:
 
574
    qemu_free (sw);
 
575
err1:
 
576
    return NULL;
 
577
}
 
578
 
 
579
SWVoice *AUD_open (SWVoice *sw, const char *name,
 
580
                   int freq, int nchannels, audfmt_e fmt)
 
581
{
 
582
    if (!audio_state.drv) {
 
583
        return NULL;
 
584
    }
 
585
 
 
586
    if (sw && freq == sw->freq && sw->nchannels == nchannels && sw->fmt == fmt) {
 
587
        return sw;
 
588
    }
 
589
 
 
590
    if (sw) {
 
591
        ldebug ("Different format %s %d %d %d\n",
 
592
                name,
 
593
                sw->freq == freq,
 
594
                sw->nchannels == nchannels,
 
595
                sw->fmt == fmt);
 
596
    }
 
597
 
 
598
    if (nchannels != 1 && nchannels != 2) {
 
599
        dolog ("Bogus channel count %d for voice %s\n", nchannels, name);
 
600
        return NULL;
 
601
    }
 
602
 
 
603
    if (!audio_state.fixed_format && sw) {
 
604
        pcm_sw_fini (sw);
 
605
        pcm_hw_del_sw (sw->hw, sw);
 
606
        pcm_hw_gc (sw->hw);
 
607
        if (sw->name) {
 
608
            qemu_free (sw->name);
 
609
            sw->name = NULL;
 
610
        }
 
611
        qemu_free (sw);
 
612
        sw = NULL;
 
613
    }
 
614
 
 
615
    if (sw) {
 
616
        HWVoice *hw = sw->hw;
 
617
        if (!hw) {
 
618
            dolog ("Internal logic error voice %s has no hardware store\n",
 
619
                   name);
 
620
            return sw;
 
621
        }
 
622
 
 
623
        if (pcm_sw_init (sw, hw, freq, nchannels, fmt)) {
 
624
            pcm_sw_fini (sw);
 
625
            pcm_hw_del_sw (hw, sw);
 
626
            pcm_hw_gc (hw);
 
627
            if (sw->name) {
 
628
                qemu_free (sw->name);
 
629
                sw->name = NULL;
 
630
            }
 
631
            qemu_free (sw);
 
632
            return NULL;
 
633
        }
 
634
    }
 
635
    else {
 
636
        sw = pcm_create_voice_pair (freq, nchannels, fmt);
 
637
        if (!sw) {
 
638
            dolog ("Failed to create voice %s\n", name);
 
639
            return NULL;
 
640
        }
 
641
    }
 
642
 
 
643
    if (sw->name) {
 
644
        qemu_free (sw->name);
 
645
        sw->name = NULL;
 
646
    }
 
647
    sw->name = qemu_strdup (name);
 
648
    return sw;
 
649
}
 
650
 
 
651
int AUD_write (SWVoice *sw, void *buf, int size)
 
652
{
 
653
    int bytes;
 
654
 
 
655
    if (!sw->hw->enabled)
 
656
        dolog ("Writing to disabled voice %s\n", sw->name);
 
657
    bytes = sw->hw->pcm_ops->write (sw, buf, size);
 
658
    return bytes;
 
659
}
 
660
 
 
661
void AUD_run (void)
 
662
{
 
663
    HWVoice *hw = NULL;
 
664
 
 
665
    while ((hw = pcm_hw_find_any_active_enabled (hw))) {
 
666
        int i;
 
667
        if (hw->pending_disable && pcm_hw_get_live (hw) <= 0) {
 
668
            hw->enabled = 0;
 
669
            hw->pcm_ops->ctl (hw, VOICE_DISABLE);
 
670
            for (i = 0; i < hw->nb_voices; i++) {
 
671
                hw->pvoice[i]->live = 0;
 
672
                /* hw->pvoice[i]->old_ticks = 0; */
 
673
            }
 
674
            continue;
 
675
        }
 
676
 
 
677
        hw->pcm_ops->run (hw);
 
678
        assert (hw->rpos < hw->samples);
 
679
        for (i = 0; i < hw->nb_voices; i++) {
 
680
            SWVoice *sw = hw->pvoice[i];
 
681
            if (!sw->active && !sw->live && sw->old_ticks) {
 
682
                int64_t delta = qemu_get_clock (vm_clock) - sw->old_ticks;
 
683
                if (delta > audio_state.ticks_threshold) {
 
684
                    ldebug ("resetting old_ticks for %s\n", sw->name);
 
685
                    sw->old_ticks = 0;
 
686
                }
 
687
            }
 
688
        }
 
689
    }
 
690
}
 
691
 
 
692
int AUD_get_free (SWVoice *sw)
 
693
{
 
694
    int free;
 
695
 
 
696
    if (!sw)
 
697
        return 4096;
 
698
 
 
699
    free = ((sw->hw->samples - sw->live) << sw->hw->shift) * sw->ratio
 
700
        / INT_MAX;
 
701
 
 
702
    free &= ~sw->hw->align;
 
703
    if (!free) return 0;
 
704
 
 
705
    return free;
 
706
}
 
707
 
 
708
int AUD_get_buffer_size (SWVoice *sw)
 
709
{
 
710
    return sw->hw->bufsize;
 
711
}
 
712
 
 
713
void AUD_adjust (SWVoice *sw, int bytes)
 
714
{
 
715
    if (!sw)
 
716
        return;
 
717
    sw->old_ticks += (ticks_per_sec * (int64_t) bytes) / sw->bytes_per_second;
 
718
}
 
719
 
 
720
void AUD_reset (SWVoice *sw)
 
721
{
 
722
    sw->active = 0;
 
723
    sw->old_ticks = 0;
 
724
}
 
725
 
 
726
int AUD_calc_elapsed (SWVoice *sw)
 
727
{
 
728
    int64_t now, delta, bytes;
 
729
    int dead, swlim;
 
730
 
 
731
    if (!sw)
 
732
        return 0;
 
733
 
 
734
    now = qemu_get_clock (vm_clock);
 
735
    delta = now - sw->old_ticks;
 
736
    bytes = (delta * sw->bytes_per_second) / ticks_per_sec;
 
737
    if (delta < 0) {
 
738
        dolog ("whoops delta(<0)=%lld\n", delta);
 
739
        return 0;
 
740
    }
 
741
 
 
742
    dead = sw->hw->samples - sw->live;
 
743
    swlim = ((dead * (int64_t) INT_MAX) / sw->ratio);
 
744
 
 
745
    if (bytes > swlim) {
 
746
        return swlim;
 
747
    }
 
748
    else {
 
749
        return bytes;
 
750
    }
 
751
}
 
752
 
 
753
void AUD_enable (SWVoice *sw, int on)
 
754
{
 
755
    int i;
 
756
    HWVoice *hw;
 
757
 
 
758
    if (!sw)
 
759
        return;
 
760
 
 
761
    hw = sw->hw;
 
762
    if (on) {
 
763
        if (!sw->live)
 
764
            sw->wpos = sw->hw->rpos;
 
765
        if (!sw->old_ticks) {
 
766
            sw->old_ticks = qemu_get_clock (vm_clock);
 
767
        }
 
768
    }
 
769
 
 
770
    if (sw->active != on) {
 
771
        if (on) {
 
772
            hw->pending_disable = 0;
 
773
            if (!hw->enabled) {
 
774
                hw->enabled = 1;
 
775
                for (i = 0; i < hw->nb_voices; i++) {
 
776
                    ldebug ("resetting voice\n");
 
777
                    sw = hw->pvoice[i];
 
778
                    sw->old_ticks = qemu_get_clock (vm_clock);
 
779
                }
 
780
                hw->pcm_ops->ctl (hw, VOICE_ENABLE);
 
781
            }
 
782
        }
 
783
        else {
 
784
            if (hw->enabled && !hw->pending_disable) {
 
785
                int nb_active = 0;
 
786
                for (i = 0; i < hw->nb_voices; i++) {
 
787
                    nb_active += hw->pvoice[i]->active != 0;
 
788
                }
 
789
 
 
790
                if (nb_active == 1) {
 
791
                    hw->pending_disable = 1;
 
792
                }
 
793
            }
 
794
        }
 
795
        sw->active = on;
 
796
    }
 
797
}
 
798
 
 
799
static struct audio_output_driver *drvtab[] = {
 
800
#ifdef USE_OSS_AUDIO
 
801
    &oss_output_driver,
 
802
#endif
 
803
#ifdef USE_FMOD_AUDIO
 
804
    &fmod_output_driver,
 
805
#endif
 
806
#ifdef USE_SDL_AUDIO
 
807
    &sdl_output_driver,
 
808
#endif
 
809
#ifdef USE_WAV_AUDIO
 
810
    &wav_output_driver,
 
811
#endif
 
812
};
 
813
 
 
814
static int voice_init (struct audio_output_driver *drv)
 
815
{
 
816
    audio_state.opaque = drv->init ();
 
817
    if (audio_state.opaque) {
 
818
        if (audio_state.nb_hw_voices > drv->max_voices) {
 
819
            dolog ("`%s' does not support %d multiple hardware channels\n"
 
820
                   "Resetting to %d\n",
 
821
                   drv->name, audio_state.nb_hw_voices, drv->max_voices);
 
822
            audio_state.nb_hw_voices = drv->max_voices;
 
823
        }
 
824
        hw_voice = qemu_mallocz (audio_state.nb_hw_voices * drv->voice_size);
 
825
        if (hw_voice) {
 
826
            audio_state.drv = drv;
 
827
            return 1;
 
828
        }
 
829
        else {
 
830
            dolog ("Not enough memory for %d `%s' voices (each %d bytes)\n",
 
831
                   audio_state.nb_hw_voices, drv->name, drv->voice_size);
 
832
            drv->fini (audio_state.opaque);
 
833
            return 0;
 
834
        }
 
835
    }
 
836
    else {
 
837
        dolog ("Could not init `%s' audio\n", drv->name);
 
838
        return 0;
 
839
    }
 
840
}
 
841
 
 
842
static void audio_vm_stop_handler (void *opaque, int reason)
 
843
{
 
844
    HWVoice *hw = NULL;
 
845
 
 
846
    while ((hw = pcm_hw_find_any (hw))) {
 
847
        if (!hw->pcm_ops)
 
848
            continue;
 
849
 
 
850
        hw->pcm_ops->ctl (hw, reason ? VOICE_ENABLE : VOICE_DISABLE);
 
851
    }
 
852
}
 
853
 
 
854
static void audio_atexit (void)
 
855
{
 
856
    HWVoice *hw = NULL;
 
857
 
 
858
    while ((hw = pcm_hw_find_any (hw))) {
 
859
        if (!hw->pcm_ops)
 
860
            continue;
 
861
 
 
862
        hw->pcm_ops->ctl (hw, VOICE_DISABLE);
 
863
        hw->pcm_ops->fini (hw);
 
864
    }
 
865
    audio_state.drv->fini (audio_state.opaque);
 
866
}
 
867
 
 
868
static void audio_save (QEMUFile *f, void *opaque)
 
869
{
 
870
}
 
871
 
 
872
static int audio_load (QEMUFile *f, void *opaque, int version_id)
 
873
{
 
874
    if (version_id != 1)
 
875
        return -EINVAL;
 
876
 
 
877
    return 0;
 
878
}
 
879
 
 
880
void AUD_init (void)
 
881
{
 
882
    int i;
 
883
    int done = 0;
 
884
    const char *drvname;
 
885
 
 
886
    audio_state.fixed_format =
 
887
        !!audio_get_conf_int (QC_FIXED_FORMAT, audio_state.fixed_format);
 
888
    audio_state.fixed_freq =
 
889
        audio_get_conf_int (QC_FIXED_FREQ, audio_state.fixed_freq);
 
890
    audio_state.nb_hw_voices =
 
891
        audio_get_conf_int (QC_VOICES, audio_state.nb_hw_voices);
 
892
 
 
893
    if (audio_state.nb_hw_voices <= 0) {
 
894
        dolog ("Bogus number of voices %d, resetting to 1\n",
 
895
               audio_state.nb_hw_voices);
 
896
    }
 
897
 
 
898
    drvname = audio_get_conf_str (QC_AUDIO_DRV, NULL);
 
899
    if (drvname) {
 
900
        int found = 0;
 
901
        for (i = 0; i < sizeof (drvtab) / sizeof (drvtab[0]); i++) {
 
902
            if (!strcmp (drvname, drvtab[i]->name)) {
 
903
                done = voice_init (drvtab[i]);
 
904
                found = 1;
 
905
                break;
 
906
            }
 
907
        }
 
908
        if (!found) {
 
909
            dolog ("Unknown audio driver `%s'\n", drvname);
 
910
        }
 
911
    }
 
912
 
 
913
    qemu_add_vm_stop_handler (audio_vm_stop_handler, NULL);
 
914
    atexit (audio_atexit);
 
915
 
 
916
    if (!done) {
 
917
        for (i = 0; !done && i < sizeof (drvtab) / sizeof (drvtab[0]); i++) {
 
918
            if (drvtab[i]->can_be_default)
 
919
                done = voice_init (drvtab[i]);
 
920
        }
 
921
    }
 
922
 
 
923
    audio_state.ticks_threshold = ticks_per_sec / 50;
 
924
    audio_state.freq_threshold = 100;
 
925
 
 
926
    register_savevm ("audio", 0, 1, audio_save, audio_load, NULL);
 
927
    if (!done) {
 
928
        dolog ("Can not initialize audio subsystem\n");
 
929
        return;
 
930
    }
 
931
 
 
932
    for (i = 0; hw_ctors[i]; i++) {
 
933
        hw_ctors[i] ();
 
934
    }
 
935
}