Statistics
| Branch: | Revision:

root / oss.c @ 08cea4ee

History | View | Annotate | Download (11.6 kB)

1 27503323 bellard
/*
2 27503323 bellard
 * QEMU OSS Audio output driver
3 27503323 bellard
 * 
4 27503323 bellard
 * Copyright (c) 2003 Vassili Karpov (malc)
5 27503323 bellard
 * 
6 27503323 bellard
 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 27503323 bellard
 * of this software and associated documentation files (the "Software"), to deal
8 27503323 bellard
 * in the Software without restriction, including without limitation the rights
9 27503323 bellard
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 27503323 bellard
 * copies of the Software, and to permit persons to whom the Software is
11 27503323 bellard
 * furnished to do so, subject to the following conditions:
12 27503323 bellard
 *
13 27503323 bellard
 * The above copyright notice and this permission notice shall be included in
14 27503323 bellard
 * all copies or substantial portions of the Software.
15 27503323 bellard
 *
16 27503323 bellard
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 27503323 bellard
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 27503323 bellard
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 27503323 bellard
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 27503323 bellard
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 27503323 bellard
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22 27503323 bellard
 * THE SOFTWARE.
23 27503323 bellard
 */
24 27503323 bellard
#include <fcntl.h>
25 27503323 bellard
#include <errno.h>
26 27503323 bellard
#include <stdio.h>
27 27503323 bellard
#include <unistd.h>
28 27503323 bellard
#include <string.h>
29 27503323 bellard
#include <stdlib.h>
30 27503323 bellard
#include <limits.h>
31 27503323 bellard
#include <inttypes.h>
32 27503323 bellard
#include <sys/types.h>
33 27503323 bellard
#include <sys/ioctl.h>
34 27503323 bellard
#include <sys/soundcard.h>
35 27503323 bellard
36 27503323 bellard
#include "vl.h"
37 27503323 bellard
38 27503323 bellard
/* http://www.df.lth.se/~john_e/gems/gem002d.html */
39 27503323 bellard
/* http://www.multi-platforms.com/Tips/PopCount.htm */
40 27503323 bellard
static inline uint32_t popcount (uint32_t u)
41 27503323 bellard
{
42 27503323 bellard
  u = ((u&0x55555555) + ((u>>1)&0x55555555));
43 27503323 bellard
  u = ((u&0x33333333) + ((u>>2)&0x33333333));
44 27503323 bellard
  u = ((u&0x0f0f0f0f) + ((u>>4)&0x0f0f0f0f));
45 27503323 bellard
  u = ((u&0x00ff00ff) + ((u>>8)&0x00ff00ff));
46 27503323 bellard
  u = ( u&0x0000ffff) + (u>>16);
47 27503323 bellard
  return u;
48 27503323 bellard
}
49 27503323 bellard
50 27503323 bellard
static inline uint32_t lsbindex (uint32_t u)
51 27503323 bellard
{
52 27503323 bellard
  return popcount ((u&-u)-1);
53 27503323 bellard
}
54 27503323 bellard
55 27503323 bellard
#define MIN(a, b) ((a)>(b)?(b):(a))
56 27503323 bellard
#define MAX(a, b) ((a)<(b)?(b):(a))
57 27503323 bellard
58 27503323 bellard
#define DEREF(x) (void)x
59 27503323 bellard
#define log(...) fprintf (stderr, "oss: " __VA_ARGS__)
60 27503323 bellard
#define ERRFail(...) do {                                       \
61 27503323 bellard
    int _errno = errno;                                         \
62 27503323 bellard
    fprintf (stderr, "oss: " __VA_ARGS__);                      \
63 27503323 bellard
    fprintf (stderr, "system error: %s\n", strerror (_errno));  \
64 27503323 bellard
    abort ();                                                   \
65 27503323 bellard
} while (0)
66 27503323 bellard
#define Fail(...) do {                          \
67 27503323 bellard
    fprintf (stderr, "oss: " __VA_ARGS__);      \
68 27503323 bellard
    fprintf (stderr, "\n");                     \
69 27503323 bellard
    abort ();                                   \
70 27503323 bellard
} while (0)
71 27503323 bellard
72 27503323 bellard
#ifdef DEBUG_OSS
73 27503323 bellard
#define lwarn(...) fprintf (stderr, "oss: " __VA_ARGS__)
74 27503323 bellard
#define linfo(...) fprintf (stderr, "oss: " __VA_ARGS__)
75 27503323 bellard
#define ldebug(...) fprintf (stderr, "oss: " __VA_ARGS__)
76 27503323 bellard
#else
77 27503323 bellard
#define lwarn(...)
78 27503323 bellard
#define linfo(...)
79 27503323 bellard
#define ldebug(...)
80 27503323 bellard
#endif
81 27503323 bellard
82 27503323 bellard
83 27503323 bellard
#define IOCTL(args) do {                        \
84 27503323 bellard
  int ret = ioctl args;                         \
85 27503323 bellard
  if (-1 == ret) {                              \
86 27503323 bellard
    ERRFail (#args);                            \
87 27503323 bellard
  }                                             \
88 27503323 bellard
  ldebug ("ioctl " #args " = %d\n", ret);       \
89 27503323 bellard
} while (0)
90 27503323 bellard
91 27503323 bellard
static int audio_fd = -1;
92 27503323 bellard
static int freq;
93 27503323 bellard
static int conf_nfrags = 4;
94 27503323 bellard
static int conf_fragsize;
95 27503323 bellard
static int nfrags;
96 27503323 bellard
static int fragsize;
97 27503323 bellard
static int bufsize;
98 27503323 bellard
static int nchannels;
99 27503323 bellard
static int fmt;
100 27503323 bellard
static int rpos;
101 27503323 bellard
static int wpos;
102 27503323 bellard
static int atom;
103 27503323 bellard
static int live;
104 27503323 bellard
static int leftover;
105 27503323 bellard
static int bytes_per_second;
106 27503323 bellard
static void *buf;
107 27503323 bellard
static enum {DONT, DSP, TID} estimate = TID;
108 27503323 bellard
109 27503323 bellard
static void (*copy_fn)(void *, void *, int);
110 27503323 bellard
111 27503323 bellard
static void copy_no_conversion (void *dst, void *src, int size)
112 27503323 bellard
{
113 27503323 bellard
    memcpy (dst, src, size);
114 27503323 bellard
}
115 27503323 bellard
116 27503323 bellard
static void copy_u16_to_s16 (void *dst, void *src, int size)
117 27503323 bellard
{
118 27503323 bellard
    int i;
119 27503323 bellard
    uint16_t *out, *in;
120 27503323 bellard
121 27503323 bellard
    out = dst;
122 27503323 bellard
    in = src;
123 27503323 bellard
124 27503323 bellard
    for (i = 0; i < size / 2; i++) {
125 27503323 bellard
        out[i] = in[i] + 0x8000;
126 27503323 bellard
    }
127 27503323 bellard
}
128 27503323 bellard
129 27503323 bellard
static void pab (struct audio_buf_info *abinfo)
130 27503323 bellard
{
131 27503323 bellard
    DEREF (abinfo);
132 27503323 bellard
133 27503323 bellard
    ldebug ("fragments %d, fragstotal %d, fragsize %d, bytes %d\n"
134 27503323 bellard
            "rpos %d, wpos %d, live %d\n",
135 27503323 bellard
            abinfo->fragments,
136 27503323 bellard
            abinfo->fragstotal,
137 27503323 bellard
            abinfo->fragsize,
138 27503323 bellard
            abinfo->bytes,
139 27503323 bellard
            rpos, wpos, live);
140 27503323 bellard
}
141 27503323 bellard
142 27503323 bellard
void AUD_reset (int rfreq, int rnchannels, audfmt_e rfmt)
143 27503323 bellard
{
144 27503323 bellard
    int fmt_;
145 27503323 bellard
    int bits16;
146 27503323 bellard
147 27503323 bellard
    if (-1 == audio_fd) {
148 27503323 bellard
        AUD_open (rfreq, rnchannels, rfmt);
149 27503323 bellard
        return;
150 27503323 bellard
    }
151 27503323 bellard
152 27503323 bellard
    switch (rfmt) {
153 27503323 bellard
    case AUD_FMT_U8:
154 27503323 bellard
        bits16 = 0;
155 27503323 bellard
        fmt_ = AFMT_U8;
156 27503323 bellard
        copy_fn = copy_no_conversion;
157 27503323 bellard
        atom = 1;
158 27503323 bellard
        break;
159 27503323 bellard
160 27503323 bellard
    case AUD_FMT_S8:
161 27503323 bellard
        Fail ("can not play 8bit signed");
162 27503323 bellard
163 27503323 bellard
    case AUD_FMT_S16:
164 27503323 bellard
        bits16 = 1;
165 27503323 bellard
        fmt_ = AFMT_S16_LE;
166 27503323 bellard
        copy_fn = copy_no_conversion;
167 27503323 bellard
        atom = 2;
168 27503323 bellard
        break;
169 27503323 bellard
170 27503323 bellard
    case AUD_FMT_U16:
171 27503323 bellard
        bits16 = 1;
172 27503323 bellard
        fmt_ = AFMT_S16_LE;
173 27503323 bellard
        copy_fn = copy_u16_to_s16;
174 27503323 bellard
        atom = 2;
175 27503323 bellard
        break;
176 27503323 bellard
177 27503323 bellard
    default:
178 27503323 bellard
        abort ();
179 27503323 bellard
    }
180 27503323 bellard
181 27503323 bellard
    if ((fmt_ == fmt) && (bits16 + 1 == nchannels) && (rfreq == freq))
182 27503323 bellard
        return;
183 27503323 bellard
    else {
184 27503323 bellard
        AUD_open (rfreq, rnchannels, rfmt);
185 27503323 bellard
    }
186 27503323 bellard
}
187 27503323 bellard
188 27503323 bellard
void AUD_open (int rfreq, int rnchannels, audfmt_e rfmt)
189 27503323 bellard
{
190 27503323 bellard
    int fmt_;
191 27503323 bellard
    int mmmmssss;
192 27503323 bellard
    struct audio_buf_info abinfo;
193 27503323 bellard
    int _fmt;
194 27503323 bellard
    int _freq;
195 27503323 bellard
    int _nchannels;
196 27503323 bellard
    int bits16;
197 27503323 bellard
198 27503323 bellard
    bits16 = 0;
199 27503323 bellard
200 27503323 bellard
    switch (rfmt) {
201 27503323 bellard
    case AUD_FMT_U8:
202 27503323 bellard
        bits16 = 0;
203 27503323 bellard
        fmt_ = AFMT_U8;
204 27503323 bellard
        copy_fn = copy_no_conversion;
205 27503323 bellard
        atom = 1;
206 27503323 bellard
        break;
207 27503323 bellard
208 27503323 bellard
    case AUD_FMT_S8:
209 27503323 bellard
        Fail ("can not play 8bit signed");
210 27503323 bellard
211 27503323 bellard
    case AUD_FMT_S16:
212 27503323 bellard
        bits16 = 1;
213 27503323 bellard
        fmt_ = AFMT_S16_LE;
214 27503323 bellard
        copy_fn = copy_no_conversion;
215 27503323 bellard
        atom = 2;
216 27503323 bellard
        break;
217 27503323 bellard
218 27503323 bellard
    case AUD_FMT_U16:
219 27503323 bellard
        bits16 = 1;
220 27503323 bellard
        fmt_ = AFMT_S16_LE;
221 27503323 bellard
        copy_fn = copy_u16_to_s16;
222 27503323 bellard
        atom = 2;
223 27503323 bellard
        break;
224 27503323 bellard
225 27503323 bellard
    default:
226 27503323 bellard
        abort ();
227 27503323 bellard
    }
228 27503323 bellard
229 27503323 bellard
    if (buf) {
230 27503323 bellard
        free (buf);
231 27503323 bellard
        buf = 0;
232 27503323 bellard
    }
233 27503323 bellard
234 27503323 bellard
    if (-1 != audio_fd)
235 27503323 bellard
        close (audio_fd);
236 27503323 bellard
237 27503323 bellard
    audio_fd = open ("/dev/dsp", O_WRONLY | O_NONBLOCK);
238 27503323 bellard
    if (-1 == audio_fd) {
239 27503323 bellard
        ERRFail ("can not open /dev/dsp");
240 27503323 bellard
    }
241 27503323 bellard
242 27503323 bellard
    _fmt = fmt_;
243 27503323 bellard
    _freq = rfreq;
244 27503323 bellard
    _nchannels = rnchannels;
245 27503323 bellard
246 27503323 bellard
    IOCTL ((audio_fd, SNDCTL_DSP_RESET, 1));
247 27503323 bellard
    IOCTL ((audio_fd, SNDCTL_DSP_SAMPLESIZE, &_fmt));
248 27503323 bellard
    IOCTL ((audio_fd, SNDCTL_DSP_CHANNELS, &_nchannels));
249 27503323 bellard
    IOCTL ((audio_fd, SNDCTL_DSP_SPEED, &_freq));
250 27503323 bellard
    IOCTL ((audio_fd, SNDCTL_DSP_NONBLOCK));
251 27503323 bellard
252 27503323 bellard
    /* from oss.pdf:
253 27503323 bellard

254 27503323 bellard
    The argument to this call is an integer encoded as 0xMMMMSSSS (in
255 27503323 bellard
    hex). The 16 least significant bits determine the fragment
256 27503323 bellard
    size. The size is 2^SSSS. For examp le SSSS=0008 gives fragment
257 27503323 bellard
    size of 256 bytes (2^8). The minimum is 16 bytes (SSSS=4) and the
258 27503323 bellard
    maximum is total_buffer_size/2. Some devices or processor
259 27503323 bellard
    architectures may require larger fragments - in this case the
260 27503323 bellard
    requested fragment size is automatically increased.
261 27503323 bellard

262 27503323 bellard
    So ahem... 4096 = 2^12, and grand total 0x0004000c
263 27503323 bellard
    */
264 27503323 bellard
265 27503323 bellard
    mmmmssss = (conf_nfrags << 16) | conf_fragsize;
266 27503323 bellard
    IOCTL ((audio_fd, SNDCTL_DSP_SETFRAGMENT, &mmmmssss));
267 27503323 bellard
268 27503323 bellard
    linfo ("_fmt = %d, fmt = %d\n"
269 27503323 bellard
           "_channels = %d, rnchannels = %d\n"
270 27503323 bellard
           "_freq = %d, freq = %d\n",
271 27503323 bellard
           _fmt, fmt_,
272 27503323 bellard
           _nchannels, rnchannels,
273 27503323 bellard
           _freq, rfreq);
274 27503323 bellard
275 27503323 bellard
    if (_fmt != fmt_) {
276 27503323 bellard
        Fail ("format %d != %d", _fmt, fmt_);
277 27503323 bellard
    }
278 27503323 bellard
279 27503323 bellard
    if (_nchannels != rnchannels) {
280 27503323 bellard
        Fail ("channels %d != %d", _nchannels, rnchannels);
281 27503323 bellard
    }
282 27503323 bellard
283 27503323 bellard
    if (_freq != rfreq) {
284 27503323 bellard
        Fail ("freq %d != %d", _freq, rfreq);
285 27503323 bellard
    }
286 27503323 bellard
287 27503323 bellard
    IOCTL ((audio_fd, SNDCTL_DSP_GETOSPACE, &abinfo));
288 27503323 bellard
289 27503323 bellard
    nfrags = abinfo.fragstotal;
290 27503323 bellard
    fragsize = abinfo.fragsize;
291 27503323 bellard
    freq = _freq;
292 27503323 bellard
    fmt = _fmt;
293 27503323 bellard
    nchannels = rnchannels;
294 27503323 bellard
    atom <<= nchannels >>  1;
295 27503323 bellard
    bufsize = nfrags * fragsize;
296 27503323 bellard
297 27503323 bellard
    bytes_per_second = (freq << (nchannels >> 1)) << bits16;
298 27503323 bellard
299 27503323 bellard
    linfo ("bytes per second %d\n", bytes_per_second);
300 27503323 bellard
301 27503323 bellard
    linfo ("fragments %d, fragstotal %d, fragsize %d, bytes %d, bufsize %d\n",
302 27503323 bellard
           abinfo.fragments,
303 27503323 bellard
           abinfo.fragstotal,
304 27503323 bellard
           abinfo.fragsize,
305 27503323 bellard
           abinfo.bytes,
306 27503323 bellard
           bufsize);
307 27503323 bellard
308 27503323 bellard
    if (NULL == buf) {
309 27503323 bellard
        buf = malloc (bufsize);
310 27503323 bellard
        if (NULL == buf) {
311 27503323 bellard
            abort ();
312 27503323 bellard
        }
313 27503323 bellard
    }
314 27503323 bellard
315 27503323 bellard
    rpos = 0;
316 27503323 bellard
    wpos = 0;
317 27503323 bellard
    live = 0;
318 27503323 bellard
}
319 27503323 bellard
320 27503323 bellard
int AUD_write (void *in_buf, int size)
321 27503323 bellard
{
322 27503323 bellard
    int to_copy, temp;
323 27503323 bellard
    uint8_t *in, *out;
324 27503323 bellard
325 27503323 bellard
    to_copy = MIN (bufsize - live, size);
326 27503323 bellard
327 27503323 bellard
    temp = to_copy;
328 27503323 bellard
329 27503323 bellard
    in = in_buf;
330 27503323 bellard
    out = buf;
331 27503323 bellard
332 27503323 bellard
    while (temp) {
333 27503323 bellard
        int copy;
334 27503323 bellard
335 27503323 bellard
        copy = MIN (temp, bufsize - wpos);
336 27503323 bellard
        copy_fn (out + wpos, in, copy);
337 27503323 bellard
338 27503323 bellard
        wpos += copy;
339 27503323 bellard
        if (wpos == bufsize) {
340 27503323 bellard
            wpos = 0;
341 27503323 bellard
        }
342 27503323 bellard
343 27503323 bellard
        temp -= copy;
344 27503323 bellard
        in += copy;
345 27503323 bellard
        live += copy;
346 27503323 bellard
    }
347 27503323 bellard
348 27503323 bellard
    return to_copy;
349 27503323 bellard
}
350 27503323 bellard
351 27503323 bellard
void AUD_run (void)
352 27503323 bellard
{
353 27503323 bellard
    int res;
354 27503323 bellard
    int bytes;
355 27503323 bellard
    struct audio_buf_info abinfo;
356 27503323 bellard
357 27503323 bellard
    if (0 == live)
358 27503323 bellard
        return;
359 27503323 bellard
360 27503323 bellard
    res = ioctl (audio_fd, SNDCTL_DSP_GETOSPACE, &abinfo);
361 27503323 bellard
362 27503323 bellard
    if (-1 == res) {
363 27503323 bellard
        int err;
364 27503323 bellard
365 27503323 bellard
        err = errno;
366 27503323 bellard
        lwarn ("SNDCTL_DSP_GETOSPACE failed with %s\n", strerror (err));
367 27503323 bellard
    }
368 27503323 bellard
369 27503323 bellard
    bytes = abinfo.bytes;
370 27503323 bellard
    bytes = MIN (live, bytes);
371 27503323 bellard
#if 0
372 27503323 bellard
    bytes = (bytes / fragsize) * fragsize;
373 27503323 bellard
#endif
374 27503323 bellard
375 27503323 bellard
    while (bytes) {
376 27503323 bellard
        int left, play, written;
377 27503323 bellard
378 27503323 bellard
        left = bufsize - rpos;
379 27503323 bellard
        play = MIN (left, bytes);
380 27503323 bellard
        written = write (audio_fd, (void *) ((uint32_t) buf + rpos), play);
381 27503323 bellard
382 27503323 bellard
        if (-1 == written) {
383 27503323 bellard
            if (EAGAIN == errno || EINTR == errno) {
384 27503323 bellard
                return;
385 27503323 bellard
            }
386 27503323 bellard
            else {
387 27503323 bellard
                ERRFail ("write audio");
388 27503323 bellard
            }
389 27503323 bellard
        }
390 27503323 bellard
391 27503323 bellard
        play = written;
392 27503323 bellard
        live -= play;
393 27503323 bellard
        rpos += play;
394 27503323 bellard
        bytes -= play;
395 27503323 bellard
396 27503323 bellard
        if (rpos == bufsize) {
397 27503323 bellard
            rpos = 0;
398 27503323 bellard
        }
399 27503323 bellard
    }
400 27503323 bellard
}
401 27503323 bellard
402 27503323 bellard
static int get_dsp_bytes (void)
403 27503323 bellard
{
404 27503323 bellard
    int res;
405 27503323 bellard
    struct count_info info;
406 27503323 bellard
407 27503323 bellard
    res = ioctl (audio_fd, SNDCTL_DSP_GETOPTR, &info);
408 27503323 bellard
    if (-1 == res) {
409 27503323 bellard
        int err;
410 27503323 bellard
411 27503323 bellard
        err = errno;
412 27503323 bellard
        lwarn ("SNDCTL_DSP_GETOPTR failed with %s\n", strerror (err));
413 27503323 bellard
        return -1;
414 27503323 bellard
    }
415 27503323 bellard
    else {
416 27503323 bellard
        ldebug ("bytes %d\n", info.bytes);
417 27503323 bellard
        return info.bytes;
418 27503323 bellard
    }
419 27503323 bellard
}
420 27503323 bellard
421 27503323 bellard
void AUD_adjust_estimate (int _leftover)
422 27503323 bellard
{
423 27503323 bellard
    leftover = _leftover;
424 27503323 bellard
}
425 27503323 bellard
426 27503323 bellard
int AUD_get_free (void)
427 27503323 bellard
{
428 27503323 bellard
    int free, elapsed;
429 27503323 bellard
430 27503323 bellard
    free = bufsize - live;
431 27503323 bellard
432 27503323 bellard
    if (0 == free)
433 27503323 bellard
        return 0;
434 27503323 bellard
435 27503323 bellard
    elapsed = free;
436 27503323 bellard
    switch (estimate) {
437 27503323 bellard
    case DONT:
438 27503323 bellard
        break;
439 27503323 bellard
440 27503323 bellard
    case DSP:
441 27503323 bellard
        {
442 27503323 bellard
            static int old_bytes;
443 27503323 bellard
            int bytes;
444 27503323 bellard
445 27503323 bellard
            bytes = get_dsp_bytes ();
446 27503323 bellard
            if (bytes <= 0)
447 27503323 bellard
                return free;
448 27503323 bellard
449 27503323 bellard
            elapsed = bytes - old_bytes;
450 27503323 bellard
            old_bytes = bytes;
451 27503323 bellard
            ldebug ("dsp elapsed %d bytes\n", elapsed);
452 27503323 bellard
            break;
453 27503323 bellard
        }
454 27503323 bellard
455 27503323 bellard
    case TID:
456 27503323 bellard
        {
457 27503323 bellard
            static uint64_t old_ticks;
458 27503323 bellard
            uint64_t ticks, delta;
459 27503323 bellard
            uint64_t ua_elapsed;
460 27503323 bellard
            uint64_t al_elapsed;
461 27503323 bellard
462 27503323 bellard
            ticks = cpu_get_ticks ();
463 27503323 bellard
            delta = ticks - old_ticks;
464 27503323 bellard
            old_ticks = ticks;
465 27503323 bellard
466 27503323 bellard
            ua_elapsed = (delta * bytes_per_second) / ticks_per_sec;
467 27503323 bellard
            al_elapsed = ua_elapsed & ~3ULL;
468 27503323 bellard
469 27503323 bellard
            ldebug ("tid elapsed %llu bytes\n", ua_elapsed);
470 27503323 bellard
471 27503323 bellard
            if (al_elapsed > (uint64_t) INT_MAX)
472 27503323 bellard
                elapsed = INT_MAX;
473 27503323 bellard
            else
474 27503323 bellard
                elapsed = al_elapsed;
475 27503323 bellard
476 27503323 bellard
            elapsed += leftover;
477 27503323 bellard
        }
478 27503323 bellard
    }
479 27503323 bellard
480 27503323 bellard
    if (elapsed > free) {
481 27503323 bellard
        lwarn ("audio can not keep up elapsed %d free %d\n", elapsed, free);
482 27503323 bellard
        return free;
483 27503323 bellard
    }
484 27503323 bellard
    else {
485 27503323 bellard
        return elapsed;
486 27503323 bellard
    }
487 27503323 bellard
}
488 27503323 bellard
489 27503323 bellard
int AUD_get_live (void)
490 27503323 bellard
{
491 27503323 bellard
    return live;
492 27503323 bellard
}
493 27503323 bellard
494 27503323 bellard
int AUD_get_buffer_size (void)
495 27503323 bellard
{
496 27503323 bellard
    return bufsize;
497 27503323 bellard
}
498 27503323 bellard
499 27503323 bellard
void AUD_init (void)
500 27503323 bellard
{
501 27503323 bellard
    int fsp;
502 27503323 bellard
    int _fragsize = 4096;
503 27503323 bellard
504 27503323 bellard
    DEREF (pab);
505 27503323 bellard
506 27503323 bellard
    fsp = _fragsize;
507 27503323 bellard
    if (0 != (fsp & (fsp - 1))) {
508 27503323 bellard
        Fail ("fragment size %d is not power of 2", fsp);
509 27503323 bellard
    }
510 27503323 bellard
511 27503323 bellard
    conf_fragsize = lsbindex (fsp);
512 27503323 bellard
}