From: Eloy D. <elo...@vo...> - 2004-04-29 12:25:13
|
Hi Steve, Thanks for the feedback! I just discovered that Borland C++ and gcc behave differently. I can do a log10(0) in gcc without causing runtime errors, but with Borland C++ it generates a "sing error" but still returns "-inf" for log10(0). It seems to be warning message. The irritating thing is that the message pops up in a message box :-S Hopefully I can disable this 'feature'... Regards, Eloy On Mon, 26 Apr 2004 16:31:32 -0400, Steve Kann wrote > Eloy Domingos wrote: > > >Hi Steve, > > > > > >Completely correct, log10(0) is -infinity :-). This will also give you > >a runtime singularity error and break your program, so this exception > >needs to be handled properly, as a well-behaved program should... :-p > > > > > I suppose this depends on what you're trying to do with the value > later. You don't get any error, for example, if you try to do this: > > #include<math.h> > > main() { > printf("%f\n", log10(0)); > } > > Which happily works for me: > > stevek@canarsie:~ $ /tmp/a.out > -inf > > Most clients will use this value to show some kind of volume level > meter. Depending on how you implement your meters, you may or may > not have any trouble with -infinity.. > > For example, in iaxcomm, HandleLevelEvent does this: > if (input < LEVEL_MIN) > input = LEVEL_MIN; > else if (input > LEVEL_MAX) > input = LEVEL_MAX; > inputLevel = (int)input - (LEVEL_MIN); > > to clamp the values and convert them to an integral value for display. > > I'm not sure what observed problem you have with -infinity, or what > you mean by runtime singularity error. But even though I haven't > checked this, and I don't remember what the particular rules are for > these "special" floating point values, I suspect that the first > conditional will always be true as long as LEVEL_MIN is a real number. > > If this was a real problem, we could resolve it by adding 1e-99 to > the value before we computed it's logarithm, but I'm not sure it's a > real problem yet. > > What is it that you're doing with the value in your callback? > Set the audio meters :-) I use similar code as in iaxcomm for the clamping of the values. > >Note that I have added some code to prevent this from happening in > >vol_to_db(). However, I was wondering whether anyone else had the same > >problem (i.e. runtime error due to log10(0)) as me. > > > >I suspect that I am just not properly setting up the audio output_level > >or something along those lines, but I haven't been able to discover > >any irregularities with my portaudio audio setup (yet). > > > > > >Eloy Domingos > > > > > >On Mon, 26 Apr 2004 10:52:55 -0400, Steve Kann wrote > > > > > >>Eloy, > >> > >> Doesn't log10(0) just give you -infinity as a result? That is > >>the correct result for us; the sound level when there's no sound is - > >>infinity decibels.. > >> > >>-SteveK > >> > >>Eloy Domingos wrote: > >> > >> > >> > >>>Hi All, > >>> > >>> > >>>Another thing which keeps bugging me is a problem with the sound system > >>>of libiaxclient (or better portaudio). I am not sure what the real cause > >>>for it is. > >>> > >>>This is the problem: > >>> > >>>In the following function from audio_encode.c, I had to build in a > >>>protection to avoid a singularity issue when calling the log10() function: > >>> > >>>--- snip --- snip ---- > >>> > >>>static double vol_to_db(double vol) > >>>{ > >>> // > >>> // protect the log10 function being called with vol=0 > >>> // > >>> if (vol<1e-99) vol=0.0001; > >>> > >>> return log10(vol) * 20; > >>>} > >>> > >>>--- snip --- snip ---- > >>> > >>>The original function just does a straight call to log10(vol) without > >>> > >>> > >check. > > > > > >>>When I traced the call, I got these references of vol_to_db(): > >>> > >>>lib\audio_encode.c(32): iaxc_do_levels_callback(vol_to_db(input_level), > >>>vol_to_db(output_level)); > >>>lib\audio_encode.c(90): volume = vol_to_db(input_level); > >>> > >>>In the end it turns out that the output_level=0 an awful lot of times, > >>>causing the log10() function to blow up. > >>> > >>>When I trace the setting of the output_level var, I get these references: > >>> > >>>lib\audio_encode.c(7): static double input_level = 0, output_level = 0; > >>>lib\audio_encode.c(103): calculate_level((short*)audio, len, > >>> > >>> > >&output_level); > > > > > >>>The calculate_level function is called to set both input_level and > >>>output_level, and is using the audio stream's data: > >>> > >>>--- snip --- snip --- > >>> > >>>static void calculate_level(short *audio, int len, double *level) { > >>> short now = 0; > >>> double nowd; > >>> int i; > >>> > >>> for(i=0;i<len;i++) > >>> if(abs(audio[i]) > now) now = abs(audio[i]); > >>> > >>> nowd = now/32767; // note: this seems useless to me > >>> > >>> *level += (((double)now/32767) - *level) / 5; > >>>} > >>> > >>>--- snip --- snip --- > >>> > >>>Which would suggest that the audio output can be zero, but the output_level > >>>is still being calculated. For some reason, the input_level does not seem > >>>to suffer from the same effect. > >>> > >>>When I enable the log10() safeguard, the softphone is fully functional, > >>>without the safeguard, you cannot run the program due to the runtime > >>>problem of doing a log10(0). > >>> > >>>Has anyone seen this problem before? Can it be avoided by certain actions > >>> > >>> > >or > > > > > >>>audio settings? > >>> > >>> > >>>Best regards, > >>>Eloy Domingos > >>> > >>> > >>> > > > > > >Vocalis Internet Open WebMail (https://webmail.vocalisinternet.com) > > > > > > Vocalis Internet Open WebMail (https://webmail.vocalisinternet.com) |