Subversion Repositories Kolibri OS

Rev

Rev 5021 | Rev 6106 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 5021 Rev 5603
1
#include 
1
#include 
2
#include 
2
#include 
3
#include 
3
#include 
4
#include "libswresample/swresample.h"
4
#include "libswresample/swresample.h"
5
 
5
 
6
#include 
6
#include 
7
#include 
7
#include 
8
#include "winlib/winlib.h"
8
#include "winlib/winlib.h"
9
#include "sound.h"
9
#include "sound.h"
10
#include "fplay.h"
10
#include "fplay.h"
11
 
11
 
12
 
12
 
13
astream_t astream;
13
astream_t astream;
14
 
14
 
15
extern uint8_t *decoder_buffer;
15
extern uint8_t *decoder_buffer;
16
int resampler_size;
16
int resampler_size;
17
volatile int sound_level_0;
17
volatile int sound_level_0;
18
volatile int sound_level_1;
18
volatile int sound_level_1;
19
 
19
 
20
volatile enum player_state player_state;
20
volatile enum player_state player_state;
21
volatile enum player_state decoder_state;
21
volatile enum player_state decoder_state;
22
volatile enum player_state sound_state;
22
volatile enum player_state sound_state;
23
 
23
 
24
extern volatile uint32_t driver_lock;
24
extern mutex_t driver_lock;
25
 
25
 
26
static SNDBUF hBuff;
26
static SNDBUF hBuff;
27
 
27
 
28
static int snd_format;
28
static int snd_format;
29
int sample_rate;
29
int sample_rate;
30
 
30
 
31
static uint32_t samples_written = 0;
31
static uint32_t samples_written = 0;
32
double audio_base = -1.0;
32
double audio_base = -1.0;
33
 
33
 
34
double get_audio_base();
34
double get_audio_base();
35
 
35
 
36
int init_audio(int format)
36
int init_audio(int format)
37
{
37
{
38
    int    err;
38
    int    err;
39
    int    version =-1;
39
    int    version =-1;
40
    char  *errstr;
40
    char  *errstr;
41
 
41
 
42
    mutex_lock(&driver_lock);
42
    mutex_lock(&driver_lock);
43
 
43
 
44
    if((err = InitSound(&version)) !=0 )
44
    if((err = InitSound(&version)) !=0 )
45
    {
45
    {
46
        mutex_unlock(&driver_lock);
46
        mutex_unlock(&driver_lock);
47
        errstr = "Sound service not installed\n\r";
47
        errstr = "Sound service not installed\n\r";
48
        goto exit_whith_error;
48
        goto exit_whith_error;
49
    };
49
    };
50
 
50
 
51
    mutex_unlock(&driver_lock);
51
    mutex_unlock(&driver_lock);
52
 
52
 
53
//    printf("sound version 0x%x\n", version);
53
//    printf("sound version 0x%x\n", version);
54
 
54
 
55
    if( (SOUND_VERSION>(version&0xFFFF)) ||
55
    if( (SOUND_VERSION>(version&0xFFFF)) ||
56
        (SOUND_VERSION<(version >> 16)))
56
        (SOUND_VERSION<(version >> 16)))
57
    {
57
    {
58
        errstr = "Sound service version mismatch\n\r";
58
        errstr = "Sound service version mismatch\n\r";
59
        goto exit_whith_error;
59
        goto exit_whith_error;
60
    }
60
    }
61
 
61
 
62
    snd_format = format;
62
    snd_format = format;
63
 
63
 
64
    create_thread(audio_thread, 0, 163840);
64
    create_thread(audio_thread, 0, 163840);
65
 
65
 
66
    return 1;
66
    return 1;
67
 
67
 
68
exit_whith_error:
68
exit_whith_error:
69
 
69
 
70
    printf(errstr);
70
    printf(errstr);
71
    return 0;
71
    return 0;
72
};
72
};
73
 
73
 
74
void set_audio_volume(int left, int right)
74
void set_audio_volume(int left, int right)
75
{
75
{
76
    SetVolume(hBuff, left, right);
76
    SetVolume(hBuff, left, right);
77
};
77
};
78
 
78
 
79
static uint64_t samples_lost;
79
static uint64_t samples_lost;
80
static double  audio_delta;
80
static double  audio_delta;
81
static double  last_time_stamp;
81
static double  last_time_stamp;
82
 
82
 
83
 
83
 
84
double get_master_clock(void)
84
double get_master_clock(void)
85
{
85
{
86
    double tstamp;
86
    double tstamp;
87
 
87
 
88
    GetTimeStamp(hBuff, &tstamp);
88
    GetTimeStamp(hBuff, &tstamp);
89
    return tstamp - audio_delta;
89
    return tstamp - audio_delta;
90
};
90
};
91
 
91
 
92
int decode_audio(AVCodecContext  *ctx, queue_t *qa)
92
int decode_audio(AVCodecContext  *ctx, queue_t *qa)
93
{
93
{
94
    static struct SwrContext *swr_ctx;
94
    static struct SwrContext *swr_ctx;
95
    static int64_t src_layout;
95
    static int64_t src_layout;
96
    static int src_freq;
96
    static int src_freq;
97
    static int src_channels;
97
    static int src_channels;
98
    static enum AVSampleFormat src_fmt = -1;
98
    static enum AVSampleFormat src_fmt = -1;
99
    static AVFrame *aFrame;
99
    static AVFrame *aFrame;
100
 
100
 
101
    AVPacket   pkt;
101
    AVPacket   pkt;
102
    AVPacket    pkt_tmp;
102
    AVPacket    pkt_tmp;
103
    int64_t dec_channel_layout;
103
    int64_t dec_channel_layout;
104
    int len, len2;
104
    int len, len2;
105
    int got_frame;
105
    int got_frame;
106
    int data_size;
106
    int data_size;
107
 
107
 
108
 
108
 
109
    if( astream.count > 192000*2)
109
    if( astream.count > 192000*2)
110
        return -1;
110
        return -1;
111
 
111
 
112
    if( get_packet(qa, &pkt) == 0 )
112
    if( get_packet(qa, &pkt) == 0 )
113
        return 0;
113
        return 0;
114
 
114
 
115
 //          __asm__("int3");
115
 //          __asm__("int3");
116
 
116
 
117
    if (!aFrame)
117
    if (!aFrame)
118
    {
118
    {
119
        if (!(aFrame = avcodec_alloc_frame()))
119
        if (!(aFrame = avcodec_alloc_frame()))
120
            return -1;
120
            return -1;
121
    } else
121
    } else
122
        avcodec_get_frame_defaults(aFrame);
122
        avcodec_get_frame_defaults(aFrame);
123
 
123
 
124
    pkt_tmp = pkt;
124
    pkt_tmp = pkt;
125
 
125
 
126
    while(pkt_tmp.size > 0)
126
    while(pkt_tmp.size > 0)
127
    {
127
    {
128
        data_size = 192000;
128
        data_size = 192000;
129
 
129
 
130
//        len = avcodec_decode_audio3(ctx,(int16_t*)decoder_buffer,
130
//        len = avcodec_decode_audio3(ctx,(int16_t*)decoder_buffer,
131
//                                   &data_size, &pkt_tmp);
131
//                                   &data_size, &pkt_tmp);
132
        got_frame = 0;
132
        got_frame = 0;
133
        len = avcodec_decode_audio4(ctx, aFrame, &got_frame, &pkt_tmp);
133
        len = avcodec_decode_audio4(ctx, aFrame, &got_frame, &pkt_tmp);
134
 
134
 
135
        if(len >= 0 && got_frame)
135
        if(len >= 0 && got_frame)
136
        {
136
        {
137
            char *samples;
137
            char *samples;
138
            int ch, plane_size;
138
            int ch, plane_size;
139
            int planar    = av_sample_fmt_is_planar(ctx->sample_fmt);
139
            int planar    = av_sample_fmt_is_planar(ctx->sample_fmt);
140
            int data_size = av_samples_get_buffer_size(&plane_size, ctx->channels,
140
            int data_size = av_samples_get_buffer_size(&plane_size, ctx->channels,
141
                                                   aFrame->nb_samples,
141
                                                   aFrame->nb_samples,
142
                                                   ctx->sample_fmt, 1);
142
                                                   ctx->sample_fmt, 1);
143
 
143
 
144
//            if(audio_base == -1.0)
144
//            if(audio_base == -1.0)
145
//            {
145
//            {
146
//                if (pkt.pts != AV_NOPTS_VALUE)
146
//                if (pkt.pts != AV_NOPTS_VALUE)
147
//                    audio_base = get_audio_base() * pkt.pts;
147
//                    audio_base = get_audio_base() * pkt.pts;
148
//                printf("audio base %f\n", audio_base);
148
//                printf("audio base %f\n", audio_base);
149
//            };
149
//            };
150
 
150
 
151
            pkt_tmp.data += len;
151
            pkt_tmp.data += len;
152
            pkt_tmp.size -= len;
152
            pkt_tmp.size -= len;
153
 
153
 
154
            dec_channel_layout =
154
            dec_channel_layout =
155
                (aFrame->channel_layout && aFrame->channels == av_get_channel_layout_nb_channels(aFrame->channel_layout)) ?
155
                (aFrame->channel_layout && aFrame->channels == av_get_channel_layout_nb_channels(aFrame->channel_layout)) ?
156
                aFrame->channel_layout : av_get_default_channel_layout(aFrame->channels);
156
                aFrame->channel_layout : av_get_default_channel_layout(aFrame->channels);
157
 
157
 
158
            if (aFrame->format          != src_fmt     ||
158
            if (aFrame->format          != src_fmt     ||
159
                dec_channel_layout      != src_layout  ||
159
                dec_channel_layout      != src_layout  ||
160
                aFrame->sample_rate     != src_freq    ||
160
                aFrame->sample_rate     != src_freq    ||
161
                !swr_ctx)
161
                !swr_ctx)
162
            {
162
            {
163
                swr_free(&swr_ctx);
163
                swr_free(&swr_ctx);
164
                swr_ctx = swr_alloc_set_opts(NULL, AV_CH_LAYOUT_STEREO, AV_SAMPLE_FMT_S16,
164
                swr_ctx = swr_alloc_set_opts(NULL, AV_CH_LAYOUT_STEREO, AV_SAMPLE_FMT_S16,
165
                                             aFrame->sample_rate, dec_channel_layout,aFrame->format,
165
                                             aFrame->sample_rate, dec_channel_layout,aFrame->format,
166
                                             aFrame->sample_rate, 0, NULL);
166
                                             aFrame->sample_rate, 0, NULL);
167
                if (!swr_ctx || swr_init(swr_ctx) < 0)
167
                if (!swr_ctx || swr_init(swr_ctx) < 0)
168
                {
168
                {
169
                    printf("Cannot create sample rate converter for conversion of %d Hz %s %d channels to %d Hz %s %d channels!\n",
169
                    printf("Cannot create sample rate converter for conversion of %d Hz %s %d channels to %d Hz %s %d channels!\n",
170
                        aFrame->sample_rate,   av_get_sample_fmt_name(aFrame->format), (int)aFrame->channels,
170
                        aFrame->sample_rate,   av_get_sample_fmt_name(aFrame->format), (int)aFrame->channels,
171
                        aFrame->sample_rate, av_get_sample_fmt_name(AV_SAMPLE_FMT_S16), 2);
171
                        aFrame->sample_rate, av_get_sample_fmt_name(AV_SAMPLE_FMT_S16), 2);
172
                    break;
172
                    break;
173
                }
173
                }
174
 
174
 
175
                src_layout   = dec_channel_layout;
175
                src_layout   = dec_channel_layout;
176
                src_channels = aFrame->channels;
176
                src_channels = aFrame->channels;
177
                src_freq     = aFrame->sample_rate;
177
                src_freq     = aFrame->sample_rate;
178
                src_fmt      = aFrame->format;
178
                src_fmt      = aFrame->format;
179
            };
179
            };
180
 
180
 
181
            if (swr_ctx)
181
            if (swr_ctx)
182
            {
182
            {
183
                const uint8_t **in = (const uint8_t **)aFrame->extended_data;
183
                const uint8_t **in = (const uint8_t **)aFrame->extended_data;
184
                uint8_t *out[] = {decoder_buffer};
184
                uint8_t *out[] = {decoder_buffer};
185
                int out_count = 192000 * 3 / 2 / av_get_bytes_per_sample(AV_SAMPLE_FMT_S16);
185
                int out_count = 192000 * 3 / 2 / av_get_bytes_per_sample(AV_SAMPLE_FMT_S16);
186
                len2 = swr_convert(swr_ctx, out, out_count, in, aFrame->nb_samples);
186
                len2 = swr_convert(swr_ctx, out, out_count, in, aFrame->nb_samples);
187
                if (len2 < 0) {
187
                if (len2 < 0) {
188
                    printf("swr_convert() failed\n");
188
                    printf("swr_convert() failed\n");
189
                    break;
189
                    break;
190
                }
190
                }
191
                if (len2 == out_count) {
191
                if (len2 == out_count) {
192
                    printf("warning: audio buffer is probably too small\n");
192
                    printf("warning: audio buffer is probably too small\n");
193
                    swr_init(swr_ctx);
193
                    swr_init(swr_ctx);
194
                }
194
                }
195
                data_size = len2 * 2 * av_get_bytes_per_sample(AV_SAMPLE_FMT_S16);
195
                data_size = len2 * 2 * av_get_bytes_per_sample(AV_SAMPLE_FMT_S16);
196
 
196
 
197
                mutex_lock(&astream.lock);
197
                mutex_lock(&astream.lock);
198
 
198
 
199
                samples = astream.buffer+astream.count;
199
                samples = astream.buffer+astream.count;
200
 
200
 
201
                memcpy(samples, decoder_buffer, data_size);
201
                memcpy(samples, decoder_buffer, data_size);
202
/*
202
/*
203
            memcpy(samples, aFrame->extended_data[0], plane_size);
203
            memcpy(samples, aFrame->extended_data[0], plane_size);
204
 
204
 
205
            if (planar && ctx->channels > 1)
205
            if (planar && ctx->channels > 1)
206
            {
206
            {
207
                uint8_t *out = ((uint8_t *)samples) + plane_size;
207
                uint8_t *out = ((uint8_t *)samples) + plane_size;
208
                for (ch = 1; ch < ctx->channels; ch++)
208
                for (ch = 1; ch < ctx->channels; ch++)
209
                {
209
                {
210
                    memcpy(out, aFrame->extended_data[ch], plane_size);
210
                    memcpy(out, aFrame->extended_data[ch], plane_size);
211
                    out += plane_size;
211
                    out += plane_size;
212
                }
212
                }
213
            }
213
            }
214
*/
214
*/
215
                astream.count += data_size;
215
                astream.count += data_size;
216
                mutex_unlock(&astream.lock);
216
                mutex_unlock(&astream.lock);
217
            };
217
            };
218
       }
218
       }
219
       else pkt_tmp.size = 0;
219
       else pkt_tmp.size = 0;
220
    }
220
    }
221
    av_free_packet(&pkt);
221
    av_free_packet(&pkt);
222
    return 1;
222
    return 1;
223
};
223
};
224
 
224
 
225
 
225
 
226
static void sync_audio(SNDBUF hbuff, int buffsize)
226
static void sync_audio(SNDBUF hbuff, int buffsize)
227
{
227
{
228
    SND_EVENT   evnt;
228
    SND_EVENT   evnt;
229
    uint32_t    offset;
229
    uint32_t    offset;
230
    double      time_stamp;
230
    double      time_stamp;
231
 
231
 
232
#ifdef BLACK_MAGIC_SOUND
232
#ifdef BLACK_MAGIC_SOUND
233
 
233
 
234
    while( player_state != CLOSED)
234
    while( player_state != CLOSED)
235
    {
235
    {
236
        GetNotify(&evnt);
236
        GetNotify(&evnt);
237
 
237
 
238
        if(evnt.code != 0xFF000001)
238
        if(evnt.code != 0xFF000001)
239
        {
239
        {
240
            printf("invalid event code %d\n\r", evnt.code);
240
            printf("invalid event code %d\n\r", evnt.code);
241
            continue;
241
            continue;
242
        }
242
        }
243
 
243
 
244
        if(evnt.stream != hbuff)
244
        if(evnt.stream != hbuff)
245
        {
245
        {
246
            printf("invalid stream %x hBuff= %x\n\r",
246
            printf("invalid stream %x hBuff= %x\n\r",
247
                    evnt.stream, hbuff);
247
                    evnt.stream, hbuff);
248
            continue;
248
            continue;
249
        }
249
        }
250
 
250
 
251
        GetTimeStamp(hbuff, &time_stamp);
251
        GetTimeStamp(hbuff, &time_stamp);
252
        audio_delta = time_stamp - last_time_stamp;
252
        audio_delta = time_stamp - last_time_stamp;
253
 
253
 
254
        offset = evnt.offset;
254
        offset = evnt.offset;
255
 
255
 
256
        mutex_lock(&astream.lock);
256
        mutex_lock(&astream.lock);
257
        {
257
        {
258
            if(astream.count < buffsize)
258
            if(astream.count < buffsize)
259
            {
259
            {
260
                memset(astream.buffer+astream.count,
260
                memset(astream.buffer+astream.count,
261
                       0, buffsize-astream.count);
261
                       0, buffsize-astream.count);
262
                astream.count = buffsize;
262
                astream.count = buffsize;
263
            };
263
            };
264
 
264
 
265
            SetBuffer(hbuff, astream.buffer, offset, buffsize);
265
            SetBuffer(hbuff, astream.buffer, offset, buffsize);
266
            samples_written+= buffsize/4;
266
            samples_written+= buffsize/4;
267
 
267
 
268
            astream.count -= buffsize;
268
            astream.count -= buffsize;
269
            if(astream.count)
269
            if(astream.count)
270
                memcpy(astream.buffer, astream.buffer+buffsize, astream.count);
270
                memcpy(astream.buffer, astream.buffer+buffsize, astream.count);
271
            mutex_unlock(&astream.lock);
271
            mutex_unlock(&astream.lock);
272
        };
272
        };
273
        break;
273
        break;
274
    };
274
    };
275
#endif
275
#endif
276
 
276
 
277
};
277
};
278
 
278
 
279
int audio_thread(void *param)
279
int audio_thread(void *param)
280
{
280
{
281
    SND_EVENT evnt;
281
    SND_EVENT evnt;
282
 
282
 
283
    int       buffsize;
283
    int       buffsize;
284
    int      samples;
284
    int      samples;
285
    int       err;
285
    int       err;
286
    char     *errstr;
286
    char     *errstr;
287
    int       active;
287
    int       active;
288
 
288
 
289
 
-
 
290
    if((err = CreateBuffer(snd_format|PCM_RING,0, &hBuff)) != 0)
289
    if((err = CreateBuffer(snd_format|PCM_RING,0, &hBuff)) != 0)
291
    {
290
    {
292
        errstr = "Cannot create sound buffer\n\r";
291
        errstr = "Cannot create sound buffer\n\r";
293
        goto exit_whith_error;
292
        goto exit_whith_error;
294
    };
293
    };
295
 
294
 
296
    SetVolume(hBuff,-1875,-1875);
295
    SetVolume(hBuff,-900,-900);
297
 
296
 
298
    if((err = GetBufferSize(hBuff, &buffsize)) != 0)
297
    if((err = GetBufferSize(hBuff, &buffsize)) != 0)
299
    {
298
    {
300
        errstr = "Cannot get buffer size\n\r";
299
        errstr = "Cannot get buffer size\n\r";
301
        goto exit_whith_error;
300
        goto exit_whith_error;
302
    };
301
    };
303
 
302
 
-
 
303
    __sync_or_and_fetch(&threads_running,AUDIO_THREAD);
-
 
304
 
304
    resampler_size = buffsize = buffsize/2;
305
    resampler_size = buffsize = buffsize/2;
305
 
306
 
306
    samples = buffsize/4;
307
    samples = buffsize/4;
307
 
308
 
308
    while( player_state != CLOSED)
309
    while( player_state != CLOSED)
309
    {
310
    {
310
        uint32_t  offset;
311
        uint32_t  offset;
311
        double    event_stamp, wait_stamp;
312
        double    event_stamp, wait_stamp;
312
        int       too_late = 0;
313
        int       too_late = 0;
313
 
314
 
314
        switch(sound_state)
315
        switch(sound_state)
315
        {
316
        {
316
            case PREPARE:
317
            case PREPARE:
317
 
318
 
318
                mutex_lock(&astream.lock);
319
                mutex_lock(&astream.lock);
319
                    if(astream.count < buffsize*2)
320
                    if(astream.count < buffsize*2)
320
                    {
321
                    {
321
                        memset(astream.buffer+astream.count,
322
                        memset(astream.buffer+astream.count,
322
                               0, buffsize*2-astream.count);
323
                               0, buffsize*2-astream.count);
323
                        astream.count = buffsize*2;
324
                        astream.count = buffsize*2;
324
                    };
325
                    };
325
 
326
 
326
                    SetBuffer(hBuff, astream.buffer, 0, buffsize*2);
327
                    SetBuffer(hBuff, astream.buffer, 0, buffsize*2);
327
                    astream.count -= buffsize*2;
328
                    astream.count -= buffsize*2;
328
                    if(astream.count)
329
                    if(astream.count)
329
                        memcpy(astream.buffer, astream.buffer+buffsize*2, astream.count);
330
                        memcpy(astream.buffer, astream.buffer+buffsize*2, astream.count);
330
                mutex_unlock(&astream.lock);
331
                mutex_unlock(&astream.lock);
331
 
332
 
332
                SetTimeBase(hBuff, audio_base);
333
                SetTimeBase(hBuff, audio_base);
333
 
334
 
334
            case PAUSE_2_PLAY:
335
            case PAUSE_2_PLAY:
335
                GetTimeStamp(hBuff, &last_time_stamp);
336
                GetTimeStamp(hBuff, &last_time_stamp);
336
//                printf("last audio time stamp %f\n", last_time_stamp);
337
//                printf("last audio time stamp %f\n", last_time_stamp);
337
 
338
 
338
                if((err = PlayBuffer(hBuff, 0)) !=0 )
339
                if((err = PlayBuffer(hBuff, 0)) !=0 )
339
                {
340
                {
340
                    errstr = "Cannot play buffer\n\r";
341
                    errstr = "Cannot play buffer\n\r";
341
                    goto exit_whith_error;
342
                    goto exit_whith_error;
342
                };
343
                };
343
                active = 1;
344
                active = 1;
344
                sync_audio(hBuff, buffsize);
345
                sync_audio(hBuff, buffsize);
345
                sound_state = PLAY;
346
                sound_state = PLAY;
346
//                printf("render: set audio latency to %f\n", audio_delta);
347
//                printf("render: set audio latency to %f\n", audio_delta);
347
 
348
 
348
                /* breaktrough */
349
                /* breaktrough */
349
 
350
 
350
            case PLAY:
351
            case PLAY:
351
                GetNotify(&evnt);
352
                GetNotify(&evnt);
352
 
353
 
353
                if(evnt.code != 0xFF000001)
354
                if(evnt.code != 0xFF000001)
354
                {
355
                {
355
                    printf("invalid event code %d\n\r", evnt.code);
356
                    printf("invalid event code %d\n\r", evnt.code);
356
                    continue;
357
                    continue;
357
                }
358
                }
358
 
359
 
359
                if(evnt.stream != hBuff)
360
                if(evnt.stream != hBuff)
360
                {
361
                {
361
                    printf("invalid stream %x hBuff= %x\n\r",
362
                    printf("invalid stream %x hBuff= %x\n\r",
362
                            evnt.stream, hBuff);
363
                            evnt.stream, hBuff);
363
                    continue;
364
                    continue;
364
                };
365
                };
365
 
366
 
366
                offset = evnt.offset;
367
                offset = evnt.offset;
367
 
368
 
368
                mutex_lock(&astream.lock);
369
                mutex_lock(&astream.lock);
369
                if(astream.count < buffsize)
370
                if(astream.count < buffsize)
370
                {
371
                {
371
                    memset(astream.buffer+astream.count,
372
                    memset(astream.buffer+astream.count,
372
                           0, buffsize-astream.count);
373
                           0, buffsize-astream.count);
373
                    astream.count = buffsize;
374
                    astream.count = buffsize;
374
                };
375
                };
375
 
376
 
376
                SetBuffer(hBuff, astream.buffer, offset, buffsize);
377
                SetBuffer(hBuff, astream.buffer, offset, buffsize);
377
 
378
 
378
                {
379
                {
379
                    double  val = 0;
380
                    double  val = 0;
380
                    int16_t *src = (int16_t*)astream.buffer;
381
                    int16_t *src = (int16_t*)astream.buffer;
381
                    int samples = buffsize/2;
382
                    int samples = buffsize/2;
382
                    int i;
383
                    int i;
383
 
384
 
384
                    for(i = 0, val = 0; i < samples/2; i++, src++)
385
                    for(i = 0, val = 0; i < samples/2; i++, src++)
385
                        if(val < abs(*src))
386
                        if(val < abs(*src))
386
                            val= abs(*src); // * *src;
387
                            val= abs(*src); // * *src;
387
 
388
 
388
                    sound_level_0 = val; //sqrt(val / (samples/2));
389
                    sound_level_0 = val; //sqrt(val / (samples/2));
389
 
390
 
390
                    for(i = 0, val = 0; i < samples/2; i++, src++)
391
                    for(i = 0, val = 0; i < samples/2; i++, src++)
391
                        if(val < abs(*src))
392
                        if(val < abs(*src))
392
                            val= abs(*src); // * *src;
393
                            val= abs(*src); // * *src;
393
 
394
 
394
                    sound_level_1 = val; //sqrt(val / (samples/2));
395
                    sound_level_1 = val; //sqrt(val / (samples/2));
395
 
396
 
396
 //                   printf("%d\n", sound_level);
397
 //                   printf("%d\n", sound_level);
397
                };
398
                };
398
 
399
 
399
                samples_written+= buffsize/4;
400
                samples_written+= buffsize/4;
400
 
401
 
401
                astream.count -= buffsize;
402
                astream.count -= buffsize;
402
                if(astream.count)
403
                if(astream.count)
403
                    memcpy(astream.buffer, astream.buffer+buffsize, astream.count);
404
                    memcpy(astream.buffer, astream.buffer+buffsize, astream.count);
404
                mutex_unlock(&astream.lock);
405
                mutex_unlock(&astream.lock);
405
                break;
406
                break;
406
 
407
 
407
            case PLAY_2_STOP:
408
            case PLAY_2_STOP:
408
                if( active )
409
                if( active )
409
                {
410
                {
410
                    ResetBuffer(hBuff, SND_RESET_ALL);
411
                    ResetBuffer(hBuff, SND_RESET_ALL);
411
                    audio_base = -1.0;
412
                    audio_base = -1.0;
412
                    active = 0;
413
                    active = 0;
413
                }
414
                }
414
                sound_state = STOP;
415
                sound_state = STOP;
415
                break;
416
                break;
416
 
417
 
417
            case PLAY_2_PAUSE:
418
            case PLAY_2_PAUSE:
418
                if( active )
419
                if( active )
419
                {
420
                {
420
                    StopBuffer(hBuff);
421
                    StopBuffer(hBuff);
421
                };
422
                };
422
                sound_state = PAUSE;
423
                sound_state = PAUSE;
423
 
424
 
424
            case PAUSE:
425
            case PAUSE:
425
            case STOP:
426
            case STOP:
426
                delay(1);
427
                delay(1);
427
        };
428
        };
428
    }
429
    }
429
 
430
 
-
 
431
    __sync_and_and_fetch(&threads_running,~AUDIO_THREAD);
-
 
432
 
430
    StopBuffer(hBuff);
433
    StopBuffer(hBuff);
431
    DestroyBuffer(hBuff);
434
    DestroyBuffer(hBuff);
432
 
435
 
433
    return 0;
436
    return 0;
434
 
437
 
435
exit_whith_error:
438
exit_whith_error:
436
 
439
 
437
    printf(errstr);
440
    printf(errstr);
438
    return -1;
441
    return -1;
439
 
442
 
440
};
443
};