mirror of
https://github.com/ZDoom/fluidsynth.git
synced 2025-04-13 11:21:06 +00:00
Evil bug fixed in ALSA driver which was causing it to terminate even if
an ALSA write error was recovered successfully, now using inline roundf replacement for dithering.
This commit is contained in:
parent
932e87f1b7
commit
b66e52e14d
7 changed files with 34 additions and 181 deletions
|
@ -115,5 +115,5 @@ Rui Nuno Capela
|
|||
Frieder Bürzele
|
||||
Henri Manson
|
||||
Mihail Zenkov
|
||||
Paul Miller
|
||||
Paul Millar
|
||||
Nick Daly
|
||||
|
|
|
@ -1,3 +1,12 @@
|
|||
2007-01-14 Josh Green <jgreen@users.sourceforge.net>
|
||||
|
||||
* src/fluid_alsa.c: Fixed evil bugs in ALSA driver where return value
|
||||
of new fluid_alsa_handle_write_error() was not being checked correctly
|
||||
causing successfully handled ALSA errors (underruns for example) to
|
||||
terminate audio thread.
|
||||
* src/fluid_synth.c: Using an inline roundi function to replace roundf
|
||||
as per suggestion by Mihail Zenkov, 16 bit for dithering.
|
||||
|
||||
2006-12-10 Josh Green <jgreen@users.sourceforge.net>
|
||||
|
||||
Lots of documentation updates.
|
||||
|
@ -13,7 +22,7 @@
|
|||
* src/fluid_aufile.c: Now also doing 16 bit dithering.
|
||||
* src/fluid_cmd.c: Removed use of old tokenizer instance.
|
||||
* src/fluid_coreaudio.c: User defined callback function is now honored.
|
||||
* src/fluid_defsfont.c: More leaks plugged (thanks to Paul Miller for
|
||||
* src/fluid_defsfont.c: More leaks plugged (thanks to Paul Millar for
|
||||
the patch), removed sfont_free_data() since sfont_close() should be
|
||||
used instead (don't want to leak a file handle).
|
||||
* src/fluid_midi_router.c: Took out uses of fflush() since sending a
|
||||
|
@ -24,7 +33,7 @@
|
|||
other improvements.
|
||||
* src/fluid_synth.c (delete_fluid_synth): Turning off all voices so that
|
||||
SoundFont data will be freed correctly (thanks to patch from
|
||||
Paul Miller).
|
||||
Paul Millar).
|
||||
* src/fluid_sys.c (fluid_strtok): New function to replace old tokenizing
|
||||
functions which required a token instance.
|
||||
* src/fluidsynth.c: Warning message printed if a non option is not a
|
||||
|
|
|
@ -478,7 +478,7 @@ static void* fluid_alsa_audio_run_float(void* d)
|
|||
|
||||
if (n < 0) /* error occurred? */
|
||||
{
|
||||
if (!fluid_alsa_handle_write_error (dev->pcm, n))
|
||||
if (fluid_alsa_handle_write_error (dev->pcm, n) != FLUID_OK)
|
||||
goto error_recovery;
|
||||
} else offset += n; /* no error occurred */
|
||||
} /* while (offset < buffer_size) */
|
||||
|
@ -498,7 +498,7 @@ static void* fluid_alsa_audio_run_float(void* d)
|
|||
|
||||
if (n < 0) /* error occurred? */
|
||||
{
|
||||
if (!fluid_alsa_handle_write_error (dev->pcm, n))
|
||||
if (fluid_alsa_handle_write_error (dev->pcm, n) != FLUID_OK)
|
||||
goto error_recovery;
|
||||
} else offset += n; /* no error occurred */
|
||||
} /* while (offset < buffer_size) */
|
||||
|
@ -563,7 +563,7 @@ static void* fluid_alsa_audio_run_s16(void* d)
|
|||
|
||||
if (n < 0) /* error occurred? */
|
||||
{
|
||||
if (!fluid_alsa_handle_write_error (dev->pcm, n))
|
||||
if (fluid_alsa_handle_write_error (dev->pcm, n) != FLUID_OK)
|
||||
goto error_recovery;
|
||||
} else offset += n; /* no error occurred */
|
||||
} /* while (offset < buffer_size) */
|
||||
|
@ -580,7 +580,7 @@ static void* fluid_alsa_audio_run_s16(void* d)
|
|||
|
||||
if (n < 0) /* error occurred? */
|
||||
{
|
||||
if (!fluid_alsa_handle_write_error (dev->pcm, n))
|
||||
if (fluid_alsa_handle_write_error (dev->pcm, n) != FLUID_OK)
|
||||
goto error_recovery;
|
||||
} else offset += n; /* no error occurred */
|
||||
} /* while (offset < buffer_size) */
|
||||
|
|
|
@ -95,4 +95,5 @@ HWND fluid_win32_get_window(void)
|
|||
{
|
||||
return fluid_wnd;
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif // #ifdef WIN32
|
||||
|
|
|
@ -1,123 +0,0 @@
|
|||
/* FluidSynth - A Software Synthesizer
|
||||
*
|
||||
* Copyright (C) 2003 Peter Hanappe and others.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public License
|
||||
* as published by the Free Software Foundation; either version 2 of
|
||||
* the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful, but
|
||||
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the Free
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
|
||||
* 02111-1307, USA
|
||||
*/
|
||||
|
||||
|
||||
#include "fluid_strtok.h"
|
||||
#include "fluidsynth_priv.h"
|
||||
|
||||
/*
|
||||
* new_fluid_strtok
|
||||
*/
|
||||
fluid_strtok_t* new_fluid_strtok(char* s, char* d)
|
||||
{
|
||||
fluid_strtok_t* st;
|
||||
st = FLUID_NEW(fluid_strtok_t);
|
||||
if (st == NULL) {
|
||||
FLUID_LOG(FLUID_ERR, "Out of memory");
|
||||
return NULL;
|
||||
}
|
||||
/* Careful! the strings are not copied for speed */
|
||||
st->string = s;
|
||||
st->delimiters = d;
|
||||
st->offset = 0;
|
||||
st->len = (s == NULL)? 0 : strlen(s);
|
||||
return st;
|
||||
}
|
||||
|
||||
int delete_fluid_strtok(fluid_strtok_t* st)
|
||||
{
|
||||
if (st == NULL) {
|
||||
FLUID_LOG(FLUID_ERR, "Null pointer");
|
||||
return 0;
|
||||
}
|
||||
free(st);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int fluid_strtok_set(fluid_strtok_t* st, char* s, char* d)
|
||||
{
|
||||
/* Careful! the strings are not copied for speed */
|
||||
st->string = s;
|
||||
st->delimiters = d;
|
||||
st->offset = 0;
|
||||
st->len = (s == NULL)? 0 : strlen(s);
|
||||
return 0;
|
||||
}
|
||||
|
||||
char* fluid_strtok_next_token(fluid_strtok_t* st)
|
||||
{
|
||||
int start = st->offset;
|
||||
int end;
|
||||
if ((st == NULL) || (st->string == NULL) || (st->delimiters == NULL)) {
|
||||
FLUID_LOG(FLUID_ERR, "Null pointer");
|
||||
return NULL;
|
||||
}
|
||||
if (start >= st->len) {
|
||||
return NULL;
|
||||
}
|
||||
while (fluid_strtok_char_index(st->string[start], st->delimiters) >= 0) {
|
||||
if (start == st->len) {
|
||||
return NULL;
|
||||
}
|
||||
start++;
|
||||
}
|
||||
end = start + 1;
|
||||
while (fluid_strtok_char_index(st->string[end], st->delimiters) < 0) {
|
||||
if (end == st->len) {
|
||||
break;
|
||||
}
|
||||
end++;
|
||||
}
|
||||
st->string[end] = 0;
|
||||
st->offset = end + 1;
|
||||
return &st->string[start];
|
||||
}
|
||||
|
||||
int fluid_strtok_has_more(fluid_strtok_t* st)
|
||||
{
|
||||
int cur = st->offset;
|
||||
if ((st == NULL) || (st->string == NULL) || (st->delimiters == NULL)) {
|
||||
FLUID_LOG(FLUID_ERR, "Null pointer");
|
||||
return -1;
|
||||
}
|
||||
while (cur < st->len) {
|
||||
if (fluid_strtok_char_index(st->string[cur], st->delimiters) < 0) {
|
||||
return -1;
|
||||
}
|
||||
cur++;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int fluid_strtok_char_index(char c, char* s)
|
||||
{
|
||||
int i;
|
||||
if (s == NULL) {
|
||||
FLUID_LOG(FLUID_ERR, "Null pointer");
|
||||
return -1;
|
||||
}
|
||||
for (i = 0; s[i] != 0; i++) {
|
||||
if (s[i] == c) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
|
@ -1,44 +0,0 @@
|
|||
/* FluidSynth - A Software Synthesizer
|
||||
*
|
||||
* Copyright (C) 2003 Peter Hanappe and others.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public License
|
||||
* as published by the Free Software Foundation; either version 2 of
|
||||
* the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful, but
|
||||
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the Free
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
|
||||
* 02111-1307, USA
|
||||
*/
|
||||
|
||||
|
||||
#ifndef _FLUID_STRTOK_H
|
||||
#define _FLUID_STRTOK_H
|
||||
|
||||
#include "fluidsynth_priv.h"
|
||||
|
||||
|
||||
/** string tokenizer */
|
||||
typedef struct {
|
||||
char* string;
|
||||
char* delimiters;
|
||||
int offset;
|
||||
int len;
|
||||
} fluid_strtok_t;
|
||||
|
||||
fluid_strtok_t* new_fluid_strtok(char* s, char* d);
|
||||
int delete_fluid_strtok(fluid_strtok_t* st);
|
||||
int fluid_strtok_set(fluid_strtok_t* st, char* s, char* d);
|
||||
char* fluid_strtok_next_token(fluid_strtok_t* st);
|
||||
int fluid_strtok_has_more(fluid_strtok_t* st);
|
||||
int fluid_strtok_char_index(char c, char* s);
|
||||
|
||||
|
||||
#endif /* _FLUID_STRTOK_H */
|
|
@ -1722,6 +1722,16 @@ static void init_dither(void)
|
|||
}
|
||||
}
|
||||
|
||||
/* A portable replacement for roundf(), seems it may actually be faster too! */
|
||||
static inline int
|
||||
roundi (float x)
|
||||
{
|
||||
if (x >= 0.0f)
|
||||
return (int)(x+0.5f);
|
||||
else
|
||||
return (int)(x-0.5f);
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_synth_write_s16
|
||||
*/
|
||||
|
@ -1740,6 +1750,7 @@ fluid_synth_write_s16(fluid_synth_t* synth, int len,
|
|||
fluid_real_t right_sample;
|
||||
double time = fluid_utime();
|
||||
int di = synth->dither_index;
|
||||
double prof_ref_on_block;
|
||||
|
||||
/* make sure we're playing */
|
||||
if (synth->state != FLUID_SYNTH_PLAYING) {
|
||||
|
@ -1752,8 +1763,7 @@ fluid_synth_write_s16(fluid_synth_t* synth, int len,
|
|||
|
||||
/* fill up the buffers as needed */
|
||||
if (cur == FLUID_BUFSIZE) {
|
||||
|
||||
double prof_ref_on_block = fluid_profile_ref();
|
||||
prof_ref_on_block = fluid_profile_ref();
|
||||
|
||||
fluid_synth_one_block(synth, 0);
|
||||
cur = 0;
|
||||
|
@ -1761,8 +1771,8 @@ fluid_synth_write_s16(fluid_synth_t* synth, int len,
|
|||
fluid_profile(FLUID_PROF_ONE_BLOCK, prof_ref_on_block);
|
||||
}
|
||||
|
||||
left_sample = left_in[cur] * 32767.0f + rand_table[0][di];
|
||||
right_sample = right_in[cur] * 32767.0f + rand_table[1][di];
|
||||
left_sample = roundi (left_in[cur] * 32766.0f + rand_table[0][di]);
|
||||
right_sample = roundi (right_in[cur] * 32766.0f + rand_table[1][di]);
|
||||
|
||||
di++;
|
||||
if (di >= DITHER_SIZE) di = 0;
|
||||
|
@ -1815,8 +1825,8 @@ fluid_synth_dither_s16(fluid_synth_t* synth, int len, float* lin, float* rin,
|
|||
|
||||
for (i = 0, j = loff, k = roff; i < len; i++, j += lincr, k += rincr) {
|
||||
|
||||
left_sample = lin[i] * 32767.0f + rand_table[0][di];
|
||||
right_sample = rin[i] * 32767.0f + rand_table[1][di];
|
||||
left_sample = roundi (lin[i] * 32766.0f + rand_table[0][di]);
|
||||
right_sample = roundi (rin[i] * 32766.0f + rand_table[1][di]);
|
||||
|
||||
di++;
|
||||
if (di >= DITHER_SIZE) di = 0;
|
||||
|
|
Loading…
Reference in a new issue