Re: A2DP quality (bluetooth-alsa)

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Mon, Oct 10, 2011 at 10:10 PM, qduaty@xxxxxxxxx <qduaty@xxxxxxxxx> wrote:
> 2011/10/10 Siarhei Siamashka <siarhei.siamashka@xxxxxxxxx>:
>> On Mon, Oct 10, 2011 at 1:40 PM, qduaty@xxxxxxxxx <qduaty@xxxxxxxxx> wrote:
>> Could you please provide a link to the Xiph Foundation's article you
>> have mentioned? Also what does "SBC is unable to encode such material
>> properly" mean?
>
> I remember it was their "About" article, but it seems either they
> shortened it (removing fragments irrelevant to their mission) or it
> has never been there and I've seen it somewhere else. Anyway, the
> whole phenomena is called "Loudness war". CD's are recorded with
> dynamics compression, so their sound has distortions introduced in
> production and high energy in all subbands at the same time. Thus, SBC
> must encode distortions as well as higher energy in all subbands.

Still I would suggest you to try the attached patch just for a test.
It reduces audio volume as part of the sbc encoding process and should
eliminate most of the possible clipping cases on the decoding side.
Some people on Hydrogenaudio forums have investigated the impact of
clipping on the perceived audio quality and found it at least audible:
    http://www.hydrogenaudio.org/forums/index.php?showtopic=82112
    http://en.wikipedia.org/wiki/Clipping_(audio)

>> The SBC decoder seems to be clamping the out-of-range values [...]
>> not doing any clamping is a lot worse and letting the samples
>> overflow results in really bad audible clicks.
>
> Maybe sin() would help, who knows? Obviously in the decoder, which
> usually cannot be reprogrammed, but future /bluez devices/ could
> benefit from this.

The headset is free to do whatever it likes with the samples falling
out of [-0x8000, 0x7FFF] range, like clipping them or adjusting the
volume or anything else. It does not have to produce files with 16-bit
audio samples but just needs to play some sound in the speakers.

>> What kind of A2DP headset are you using yourself?
>
> Nokia BT-503. Its quality is enough to notice an obvious difference
> between 'computer' bitpool (<=53) and that coming from Windows Mobile
> (128 does not cause skipping yet). In presence of dynamics
> compression, even two guitars with a vocal can be distinguished only
> with higher bitpool. Another example is a symphony - I can hear
> individual instruments from WinMo, and a "movie soundtrack" from
> Bluez. I don't know how the device deals with clicks, but I never
> heard them. Usual (and also annoying) distortion is a 'chirp' in some
> bands.

OK, thanks for the information. It looks like this is not the same
issue as I observed with Logitech FreePulse headset. In any case, I'm
glad that you are interested in A2DP audio quality and would
definitely appreciate any feedback and test results. As I see it,
there are two things to take care:
    1. make higher sbc bitpool settings usable in bluez with your headset
    2. make sure that sbc codec itself is well behaved and providing
the best results for any available bitpool
But I myself can only comment on the latter.

Using bitpool 128 is kind of weird for SBC codec, because the encoded
data stream has about the same size as the the original data and this
defeats the whole purpose of having any lossy compression at all. It
is also worth mentioning that bluez sbc encoder implementation uses a
bit lower precision analysis filter by default which allows SIMD
optimizations and this should be fine at normal encoding settings. But
uncommenting SBC_HIGH_PRECISION define may be important for getting
better audio quality at higher bitpool settings. Also trying to
enable/disable joint stereo, testing 4 vs. 8 subbands and snr vs.
loudness allocation method may probably have some impact on audio
quality for your use case. I still recommend you to try sbcenc/sbcdec
tools for the experiments with audio quality. They use a somewhat less
common big endian http://en.wikipedia.org/wiki/Au_file_format but you
can get your audio files converted to it using
http://sox.sourceforge.net/ command line tool. Also here I have some
ruby script, which can simplify sbc encoding/decoding testing:
    http://cgit.freedesktop.org/~siamashka/bluez/log/?h=sbc-tests

When doing the evaluation of encoding/decoding audio quality with
sbcenc/sbcdec, please keep in mind that the current bluez sbc
*decoder* implementation has some issues. Partially motivated by your
posts, I decided to finally attempt to bring the bluez sbc decoder
into a better shape and already sent one patch to the mailing list for
review. The rest of the fixes are available here and they improve sbc
decoder audio quality:
    http://cgit.freedesktop.org/~siamashka/bluez/log/?h=sbc-decoder-fixes
But the synthesis filter still needs to be converted to fixed point
and optimized for performance before really using it in bluez. I'll
try to do this work as time permits and will submit the patches later.
But quality-wise, it should be already possible to use my
'sbc-decoder-fixes' git branch for testing.

-- 
Best regards,
Siarhei Siamashka
From 123a021376a4fd66c88fc1ed6ca26a6e8ee5e365 Mon Sep 17 00:00:00 2001
From: Siarhei Siamashka <siarhei.siamashka@xxxxxxxxx>
Date: Tue, 18 Oct 2011 04:08:07 +0300
Subject: [PATCH] HACK: sbc: reduce volume in sbc encoder

Reducing audio volume when encoding helps to avoid clipping
in the decoder for the heavily dynamically compressed audio.
Also high precision mode is enabled in sbc encoder to get the
best possible audio quality.

Some references:
    http://en.wikipedia.org/wiki/Loudness_war
    http://www.hydrogenaudio.org/forums/index.php?showtopic=82112
---
 sbc/sbc_tables.h |    6 +++---
 1 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/sbc/sbc_tables.h b/sbc/sbc_tables.h
index 28c0d54..8d025e0 100644
--- a/sbc/sbc_tables.h
+++ b/sbc/sbc_tables.h
@@ -136,7 +136,7 @@ static const int32_t synmatrix8[16][8] = {
 
 /* Uncomment the following line to enable high precision build of SBC encoder */
 
-/* #define SBC_HIGH_PRECISION */
+#define SBC_HIGH_PRECISION
 
 #ifdef SBC_HIGH_PRECISION
 #define FIXED_A int64_t /* data type for fixed point accumulator */
@@ -208,7 +208,7 @@ static const FIXED_T _sbc_proto_fixed4[40] = {
  */
 #define SBC_COS_TABLE_FIXED4_SCALE \
 	((sizeof(FIXED_T) * CHAR_BIT - 1) + SBC_FIXED_EXTRA_BITS)
-#define F_COS4(x) (FIXED_A) ((x) * \
+#define F_COS4(x) (FIXED_A) ((x * 0.7) * \
 	((FIXED_A) 1 << (sizeof(FIXED_T) * CHAR_BIT - 1)) + 0.5)
 #define F(x) F_COS4(x)
 static const FIXED_T cos_table_fixed_4[32] = {
@@ -305,7 +305,7 @@ static const FIXED_T _sbc_proto_fixed8[80] = {
  */
 #define SBC_COS_TABLE_FIXED8_SCALE \
 	((sizeof(FIXED_T) * CHAR_BIT - 1) + SBC_FIXED_EXTRA_BITS)
-#define F_COS8(x) (FIXED_A) ((x) * \
+#define F_COS8(x) (FIXED_A) ((x * 0.7) * \
 	((FIXED_A) 1 << (sizeof(FIXED_T) * CHAR_BIT - 1)) + 0.5)
 #define F(x) F_COS8(x)
 static const FIXED_T cos_table_fixed_8[128] = {
-- 
1.7.3.4


[Index of Archives]     [Bluez Devel]     [Linux Wireless Networking]     [Linux Wireless Personal Area Networking]     [Linux ATH6KL]     [Linux USB Devel]     [Linux Media Drivers]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Big List of Linux Books]

  Powered by Linux