philippe44 / AirConnect

Use AirPlay to stream to UPnP/Sonos & Chromecast devices
Other
3.53k stars 218 forks source link

Option for force bitrate-resolution #30

Closed lars18th closed 6 years ago

lars18th commented 6 years ago

Hi,

My environment is like this: one ChromeAudio connected via SPDIF (optical output) to a receiver (DD & DTS compatible).

Now, I have this good project working (Thank you to the developer!). :smile:

However, I like to have "bit-perfect" output over the optical output. To check this, I use DTSWAV files (one DTS bitstream encapsulated over an standard PCM 44.1/16bit file). At time, all my test will fail! Using one Airport Express with the same configuration I don't have any problem to play these files using iTunes and configuring it for not change the audio stream. However, I can't do it with this tool. My assumption is that the Chromecast it's using 48KHz/24bit (or similar) and this tool is reencoding. So, I suggest to enable the option for force the bitrate-resolution (in my case: 44.1/bit). With this will be possible to have a bit-perfect output (required for DTS CD).

If you need some testing files, you can download free samples from here: http://www.ambisonic.net/nimbus-sample.html (get the DTS-WAV file at http://www.ambisonic.net/decodes/elgar-excerpt-dts.wav).

Regards.

philippe44 commented 6 years ago

By default, AirCast expects an alac-encoded stream, decodes it and re-encodes it as flac. ALAC can be plain, the decoder handles that. I think that all you need to do is to change, in the config file, the option to use wav instead of flac re-encoding. See README file

lars18th commented 6 years ago

Hi @philippe44 ,

Thank you for your response! :smile:

I tryed it. However, it doesn't work. In fact, FLAC is lossless, so this should not be problem. The possible problem is the 44.1 -> 48 conversion (if the bit depth is 16 and not 24). You know how to force in the Chromecast protocol to use an specific format (i.e stereo/44.1/16bit)?

Futhermore, can you include a debug option in your tool for saving the output stream? This will be very useful for "bit-perfect" debugging, as we can load the output file in some audio tool and review it. You agree?

Regards!

lars18th commented 6 years ago

Hi @philippe44 ,

I do more tests for discarding other problems. For example, I do this test:

The conclusion is then: The Chromecast Audio can do a "bit-perfect" play of 44.1/16bit/Stereo PCM sound (if not, then we can't play these DTS files encapsulated using the IEC 61937 standard).

In my failed tests the player is iTunes. On it I have configured "play as 44.1 kHz 16bit". Then I select the AirPlay device corresponding to the Chromecast Audio. But the output sound it's then "white noise" and not the DTS track. Futhermore, if I use an Airport Express I can hear the correct audio. So, my assumption is that the AirConnect is doing some "audio resampling". And for sure, I'm configured AirConnect to use "WAV".

Please, can you help me with this trouble? If you need some DTSWAV files for testing, I can share some free samples with you. Thank you!

lars18th commented 6 years ago

Hi @philippe44 ,

Another (perhaps) useful information: I do a lot of tests changing the parameter "". For a "bit-perfect" output it's required to not modify the samples at all. So, if you are doing some "volume change", then the output will be modified. Setting this parameter to "1.0" I can't produce a better result. However, I see that regular audio (non-DTS) is quite loud using this value. So, I suspect that the values "0.5" likes to target "normal volume". However, perhaps you're doing some resample when this value is "0.5".

In summary, can you add the option for "disable the volume changes"? This will force to not modify the volume of the target and use all the time the samples as original.

What you think? Regards!

philippe44 commented 6 years ago

The samples are already not modified at all. There is no computing made on them. Volume is the CC hardware volume, so samples are untouched before they arrive to the CC which then does what he wants. The only thing is that a wav header is added at the beginning of the HTTP connection and I would assume that this is where something happens. I don't know DTSWAV but there is likley something funny done witht he wav header so that the client can figure out that this is not plain PCM samples

lars18th commented 6 years ago

Hi @philippe44 ,

The samples are already not modified at all

This is really true when using the configuration described before (using the App "HiBy music").

I don't know DTSWAV

OK, so a fast description: In order to send compressed audio formats over the SPDIF digital connection, Dolby Labs and DTS Company have developed the standard IEC 61937. This is a method for sending a payload over an STEREO 16bit bitstream. The concept is quite simple: the audio samples are simple BYTES of the bitstream. A magic number it's used as header and when the decoder detects this header, it changes from WAV play to DD/DTS decoding. Then the compressed bitstream is transmitted and zeroes are used for padding. So, if you "play" a compressed bitstream without the decoder, then you listen noise (mainly like a "white noise"). The problem is the maximum bitrate: using 44.1KHz you can only send up to 1411kbps, and using 48KHz only 1536kbps. This is the reason for this top bitrate for DD and DTS soundtracks, and the reason for not supporting HD Audio (DTS-MasterAudio and DD TrueHD) over SPDIF (but over HDMI). Then a DTSWAV file is a PCM WAV file encapsulating a DTS bitstream using the IEC 61937 standard.

So, one side effect of playing a DTS bitstream (or DD 5.1) and sending it to a receiver over a SPDIF connection (optical or RCA), it's that it can only decoded if the bitstream is a "perfect bit copy" of the original. Then if you "play" a DTSWAV file, and your "network" (transmitter medium) not changes the samples, and then the decoder is compatible, then you can hear it.

In order to achieve this functionality, I suggest that we work together. You agree?

philippe44 commented 6 years ago

Thanks for the description. I need to read more about dtswav, but is the special header at the beginning of the 'samples' or is this in the wav header? That sounds to me like the main reason why it does not work today. As said before, I receive audio data from airplay device. It goes through the ´official' alac decoder which means I now have a 1411kbps stream, which is bit exact what was fed to the airplay source. Then, unless flac is used, that decoded data is sent without modification to the CC device. The only thing that I add is, at the beginning, a wav header - hence I think the problem is there

lars18th commented 6 years ago

Hi @philippe44 ,

is the special header at the beginning of the 'samples' or is this in the wav header?

The "header" isn't related in any sense with the WAV header. In fact, isn't related with WAV file format. The DTS (and DD) "header" is a simple MAGIC-NUMBER expressed as a SAMPLES (inside the bitstream, aka WAV samples). That is, if the receiver gets one of this sample sequence, then it assumes it's a DTS bitstream: "7F FE 80 01" or "1F FF E8 00 07 F_". And YES, that are simple "samples"... See more here: https://wiki.multimedia.cx/index.php/DTS

Futhermore, this "header" it's a SYNC mark. So a DTS bitstream is in the form of: SYNC-HEADER, PAYLOAD (packed bitstream in DTS format), PADDING... repeated forever. This is the way used by the standard IEC 61937 for send any compressed bitstream as "samples" (SYNC,PAYLOAD,PADDING).

Then, unless flac is used, that decoded data is sent without modification to the CC device.

So, as FLAC is LOSSLESS then will be irrelevant to use FLAC or WAV. The result needs to be the same. Perhaps you will like to first introduce the option for save the bitstream. Then we can compare the original file with the bitstream sended to the Chromecast. Perhaps, something isn't a perfect bit-copy.

You agree?

philippe44 commented 6 years ago

I was making some changes to store files and then I realized that I totally forgot to ask you if you have set the latency parameters to x:0 (set the http latency to 0)? Without that, there are silence frames added at the beginning of the http transmit which 100% cause your problem. I was in the middle of making the change to store incoming RTP, decoded audio and then outgoing HTTP anyway, but I've now confirmed that the existing version, with x:0 does send bit exact files

philippe44 commented 6 years ago

Still here? if not I'll close the issue

lars18th commented 6 years ago

Hi @philippe44 ,

I'll check it and I comment here. Sorry for the delay. Please, not close the issue.