Go to:
Gentoo Home
Documentation
Forums
Lists
Bugs
Planet
Store
Wiki
Get Gentoo!
Gentoo's Bugzilla – Attachment 182055 Details for
Bug 259009
New ebuild: MythTV-0.21 with backported support for HDPVR and VPDAU
Home
|
New
–
[Ex]
|
Browse
|
Search
|
Privacy Policy
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Audio encoding patch for VPDAU in MythTV
mythtv-0.21-audioencoding-fixes-vdpau-6.patch (text/plain), 79.04 KB, created by
Marshall McMullen
on 2009-02-14 21:16:02 UTC
(
hide
)
Description:
Audio encoding patch for VPDAU in MythTV
Filename:
MIME Type:
Creator:
Marshall McMullen
Created:
2009-02-14 21:16:02 UTC
Size:
79.04 KB
patch
obsolete
>diff -Naur --exclude=.svn a/libs/libmyth/audiooutput.h b/libs/libmyth/audiooutput.h >--- a/libs/libmyth/audiooutput.h 2009-01-22 12:22:24.000000000 +1100 >+++ b/libs/libmyth/audiooutput.h 2009-01-28 15:49:56.000000000 +1100 >@@ -34,11 +34,11 @@ > virtual void Reconfigure(int audio_bits, > int audio_channels, > int audio_samplerate, >- bool audio_passthru, >- void* audio_codec = NULL) = 0; >+ bool audio_passthru) = 0; > > virtual void SetStretchFactor(float factor); > virtual float GetStretchFactor(void) { return 1.0f; } >+ virtual bool ToggleUpmix(void) = 0; > > // do AddSamples calls block? > virtual void SetBlocking(bool blocking) = 0; >diff -Naur --exclude=.svn a/libs/libmyth/audiooutputalsa.cpp b/libs/libmyth/audiooutputalsa.cpp >--- a/libs/libmyth/audiooutputalsa.cpp 2009-01-22 12:22:24.000000000 +1100 >+++ b/libs/libmyth/audiooutputalsa.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -35,6 +35,55 @@ > AudioOutputALSA::~AudioOutputALSA() > { > KillAudio(); >+ SetIECStatus(true); >+} >+ >+void AudioOutputALSA::SetIECStatus(bool audio) { >+ >+ snd_ctl_t *ctl; >+ const char *spdif_str = SND_CTL_NAME_IEC958("", PLAYBACK, DEFAULT); >+ int spdif_index = -1; >+ snd_ctl_elem_list_t *clist; >+ snd_ctl_elem_id_t *cid; >+ snd_ctl_elem_value_t *cval; >+ snd_aes_iec958_t iec958; >+ int cidx, controls; >+ >+ VERBOSE(VB_AUDIO, QString("Setting IEC958 status: %1") >+ .arg(audio ? "audio" : "non-audio")); >+ >+ snd_ctl_open(&ctl, "default", 0); >+ snd_ctl_elem_list_alloca(&clist); >+ snd_ctl_elem_list(ctl, clist); >+ snd_ctl_elem_list_alloc_space(clist, snd_ctl_elem_list_get_count(clist)); >+ snd_ctl_elem_list(ctl, clist); >+ controls = snd_ctl_elem_list_get_used(clist); >+ for (cidx = 0; cidx < controls; cidx++) >+ { >+ if (!strcmp(snd_ctl_elem_list_get_name(clist, cidx), spdif_str)) >+ if (spdif_index < 0 || >+ snd_ctl_elem_list_get_index(clist, cidx) == (uint)spdif_index) >+ break; >+ } >+ >+ if (cidx >= controls) >+ return; >+ >+ snd_ctl_elem_id_alloca(&cid); >+ snd_ctl_elem_list_get_id(clist, cidx, cid); >+ snd_ctl_elem_value_alloca(&cval); >+ snd_ctl_elem_value_set_id(cval, cid); >+ snd_ctl_elem_read(ctl,cval); >+ snd_ctl_elem_value_get_iec958(cval, &iec958); >+ >+ if (!audio) >+ iec958.status[0] |= IEC958_AES0_NONAUDIO; >+ else >+ iec958.status[0] &= ~IEC958_AES0_NONAUDIO; >+ >+ snd_ctl_elem_value_set_iec958(cval, &iec958); >+ snd_ctl_elem_write(ctl, cval); >+ > } > > bool AudioOutputALSA::OpenDevice() >@@ -42,15 +91,24 @@ > snd_pcm_format_t format; > unsigned int buffer_time, period_time; > int err; >+ QString real_device; > > if (pcm_handle != NULL) > CloseDevice(); > > pcm_handle = NULL; > numbadioctls = 0; >- >- QString real_device = (audio_passthru) ? >- audio_passthru_device : audio_main_device; >+ >+ if (audio_passthru || audio_enc) >+ { >+ real_device = audio_passthru_device; >+ SetIECStatus(false); >+ } >+ else >+ { >+ real_device = audio_main_device; >+ SetIECStatus(true); >+ } > > VERBOSE(VB_GENERAL, QString("Opening ALSA audio device '%1'.") > .arg(real_device)); >diff -Naur --exclude=.svn a/libs/libmyth/audiooutputalsa.h b/libs/libmyth/audiooutputalsa.h >--- a/libs/libmyth/audiooutputalsa.h 2009-01-22 12:22:24.000000000 +1100 >+++ b/libs/libmyth/audiooutputalsa.h 2009-01-28 15:49:56.000000000 +1100 >@@ -37,6 +37,7 @@ > virtual inline int getBufferedOnSoundcard(void); > > private: >+ void SetIECStatus(bool audio); > inline int SetParameters(snd_pcm_t *handle, > snd_pcm_format_t format, unsigned int channels, > unsigned int rate, unsigned int buffer_time, >diff -Naur --exclude=.svn a/libs/libmyth/audiooutputbase.cpp b/libs/libmyth/audiooutputbase.cpp >--- a/libs/libmyth/audiooutputbase.cpp 2009-01-22 12:22:24.000000000 +1100 >+++ b/libs/libmyth/audiooutputbase.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -37,9 +37,9 @@ > > audio_main_device(QDeepCopy<QString>(laudio_main_device)), > audio_passthru_device(QDeepCopy<QString>(laudio_passthru_device)), >- audio_passthru(false), audio_stretchfactor(1.0f), >+ audio_passthru(false), audio_enc(false), >+ audio_reenc(false), audio_stretchfactor(1.0f), > >- audio_codec(NULL), > source(lsource), killaudio(false), > > pauseaudio(false), audio_actually_paused(false), >@@ -54,10 +54,13 @@ > pSoundStretch(NULL), > encoder(NULL), > upmixer(NULL), >+ > source_audio_channels(-1), >+ source_audio_samplerate(0), > source_audio_bytes_per_sample(0), > needs_upmix(false), > surround_mode(FreeSurround::SurroundModePassive), >+ old_audio_stretchfactor(1.0), > > blocking(false), > >@@ -84,6 +87,9 @@ > memset(&audiotime_updated, 0, sizeof(audiotime_updated)); > memset(audiobuffer, 0, sizeof(char) * AUDBUFSIZE); > configured_audio_channels = gContext->GetNumSetting("MaxChannels", 2); >+ orig_config_channels = configured_audio_channels; >+ allow_ac3_passthru = gContext->GetNumSetting("AC3PassThru", false); >+ src_quality = gContext->GetNumSetting("SRCQuality", 2); > > // You need to call Reconfigure from your concrete class. > // Reconfigure(laudio_bits, laudio_channels, >@@ -124,40 +130,9 @@ > VERBOSE(VB_GENERAL, LOC + QString("Using time stretch %1") > .arg(audio_stretchfactor)); > pSoundStretch = new soundtouch::SoundTouch(); >- if (audio_codec) >- { >- if (!encoder) >- { >- VERBOSE(VB_AUDIO, LOC + >- QString("Creating Encoder for codec %1 origfs %2") >- .arg(audio_codec->codec_id) >- .arg(audio_codec->frame_size)); >- >- encoder = new AudioOutputDigitalEncoder(); >- if (!encoder->Init(audio_codec->codec_id, >- audio_codec->bit_rate, >- audio_codec->sample_rate, >- audio_codec->channels >- )) >- { >- // eeks >- delete encoder; >- encoder = NULL; >- VERBOSE(VB_AUDIO, LOC + >- QString("Failed to Create Encoder")); >- } >- } >- } >- if (audio_codec && encoder) >- { >- pSoundStretch->setSampleRate(audio_codec->sample_rate); >- pSoundStretch->setChannels(audio_codec->channels); >- } >- else >- { >- pSoundStretch->setSampleRate(audio_samplerate); >- pSoundStretch->setChannels(audio_channels); >- } >+ pSoundStretch->setSampleRate(audio_samplerate); >+ pSoundStretch->setChannels(upmixer ? >+ configured_audio_channels : source_audio_channels); > > pSoundStretch->setTempo(audio_stretchfactor); > pSoundStretch->setSetting(SETTING_SEQUENCE_MS, 35); >@@ -165,7 +140,6 @@ > // dont need these with only tempo change > //pSoundStretch->setPitch(1.0); > //pSoundStretch->setRate(1.0); >- > //pSoundStretch->setSetting(SETTING_USE_QUICKSEEK, true); > //pSoundStretch->setSetting(SETTING_USE_AA_FILTER, false); > } >@@ -184,35 +158,33 @@ > return audio_stretchfactor; > } > >+bool AudioOutputBase::ToggleUpmix(void) >+{ >+ if (orig_config_channels == 2 || audio_passthru) >+ return false; >+ if (configured_audio_channels == 6) >+ configured_audio_channels = 2; >+ else >+ configured_audio_channels = 6; >+ >+ Reconfigure(audio_bits, source_audio_channels, >+ source_audio_samplerate, audio_passthru); >+ return (configured_audio_channels == 6); >+} >+ > void AudioOutputBase::Reconfigure(int laudio_bits, int laudio_channels, >- int laudio_samplerate, bool laudio_passthru, >- void *laudio_codec) >+ int laudio_samplerate, bool laudio_passthru) > { >- int codec_id = CODEC_ID_NONE; >- int lcodec_id = CODEC_ID_NONE; >- int lcchannels = 0; >- int cchannels = 0; > int lsource_audio_channels = laudio_channels; > bool lneeds_upmix = false; >- >- if (laudio_codec) >- { >- lcodec_id = ((AVCodecContext*)laudio_codec)->codec_id; >- laudio_bits = 16; >- laudio_channels = 2; >- lsource_audio_channels = laudio_channels; >- laudio_samplerate = 48000; >- lcchannels = ((AVCodecContext*)laudio_codec)->channels; >- } >- >- if (audio_codec) >- { >- codec_id = audio_codec->codec_id; >- cchannels = ((AVCodecContext*)audio_codec)->channels; >- } >- >- if ((configured_audio_channels == 6) && >- !(laudio_codec || audio_codec)) >+ bool laudio_reenc = false; >+ >+ // Are we perhaps reencoding a (previously) timestretched bitstream? >+ if (laudio_channels > 2 && !laudio_passthru) >+ laudio_reenc = true; >+ >+ // Enough channels? Upmix if not >+ if (laudio_channels < configured_audio_channels && !laudio_passthru) > { > laudio_channels = configured_audio_channels; > lneeds_upmix = true; >@@ -225,7 +197,7 @@ > laudio_samplerate == audio_samplerate && !need_resampler && > laudio_passthru == audio_passthru && > lneeds_upmix == needs_upmix && >- lcodec_id == codec_id && lcchannels == cchannels); >+ laudio_reenc == audio_reenc); > bool upmix_deps = > (lsource_audio_channels == source_audio_channels); > if (general_deps && upmix_deps) >@@ -252,12 +224,11 @@ > waud = raud = 0; > audio_actually_paused = false; > >- bool redo_stretch = (pSoundStretch && audio_channels != laudio_channels); > audio_channels = laudio_channels; > source_audio_channels = lsource_audio_channels; > audio_bits = laudio_bits; >- audio_samplerate = laudio_samplerate; >- audio_codec = (AVCodecContext*)laudio_codec; >+ source_audio_samplerate = audio_samplerate = laudio_samplerate; >+ audio_reenc = laudio_reenc; > audio_passthru = laudio_passthru; > needs_upmix = lneeds_upmix; > >@@ -268,8 +239,6 @@ > Error("AudioOutput only supports 8 or 16bit audio."); > return; > } >- audio_bytes_per_sample = audio_channels * audio_bits / 8; >- source_audio_bytes_per_sample = source_audio_channels * audio_bits / 8; > > need_resampler = false; > killaudio = false; >@@ -278,7 +247,58 @@ > internal_vol = gContext->GetNumSetting("MythControlsVolume", 0); > > numlowbuffer = 0; >+ >+ // Encode to AC-3 if not passing thru, there's more than 2 channels >+ // and we're allowed to passthru AC-3 >+ // This won't reencode timestretched 2ch AC-3 but there's no point doing so >+ if (!audio_passthru && audio_channels > 2 && allow_ac3_passthru) >+ { >+ VERBOSE(VB_AUDIO, LOC + "Creating AC-3 Encoder"); >+ int srate = src_quality == 0 ? audio_samplerate : 48000; >+ encoder = new AudioOutputDigitalEncoder(); >+ if (!encoder->Init(CODEC_ID_AC3, 448000, srate, >+ audio_channels, audio_reenc)) >+ { >+ VERBOSE(VB_AUDIO, LOC + "Can't create AC-3 encoder"); >+ delete encoder; >+ encoder = NULL; >+ } >+ >+ audio_enc = true; >+ } >+ >+ if(audio_passthru || audio_enc) >+ // AC-3 output - soundcard expects a 2ch 48k stream >+ audio_channels = 2; >+ >+ audio_bytes_per_sample = audio_channels * audio_bits / 8; >+ source_audio_bytes_per_sample = source_audio_channels * audio_bits / 8; > >+ // Always resample to 48k - many cards can't do anything else >+ // and ALSA will do it with linear interpolation (yuk) if we don't anyway >+ if (src_quality != 0 && audio_samplerate != 48000) >+ { >+ int error; >+ audio_samplerate = 48000; >+ VERBOSE(VB_GENERAL, LOC + QString("Using resampler. From: %1 to %2") >+ .arg(laudio_samplerate).arg(audio_samplerate)); >+ src_ctx = src_new(3-src_quality, audio_channels, &error); >+ if (error) >+ { >+ Error(QString("Error creating resampler, the error was: %1") >+ .arg(src_strerror(error)) ); >+ pthread_mutex_unlock(&avsync_lock); >+ pthread_mutex_unlock(&audio_buflock); >+ src_ctx = NULL; >+ return; >+ } >+ src_data.src_ratio = (double) audio_samplerate / laudio_samplerate; >+ src_data.data_in = src_in; >+ src_data.data_out = src_out; >+ src_data.output_frames = 16384*6; >+ need_resampler = true; >+ } >+ > VERBOSE(VB_GENERAL, QString("Opening audio device '%1'. ch %2(%3) sr %4") > .arg(audio_main_device).arg(audio_channels) > .arg(source_audio_channels).arg(audio_samplerate)); >@@ -314,32 +334,8 @@ > current_seconds = -1; > source_bitrate = -1; > >- // NOTE: this won't do anything as above samplerate vars are set equal >- // Check if we need the resampler >- if (audio_samplerate != laudio_samplerate) >- { >- int error; >- VERBOSE(VB_GENERAL, LOC + QString("Using resampler. From: %1 to %2") >- .arg(laudio_samplerate).arg(audio_samplerate)); >- src_ctx = src_new (SRC_SINC_BEST_QUALITY, audio_channels, &error); >- if (error) >- { >- Error(QString("Error creating resampler, the error was: %1") >- .arg(src_strerror(error)) ); >- pthread_mutex_unlock(&avsync_lock); >- pthread_mutex_unlock(&audio_buflock); >- return; >- } >- src_data.src_ratio = (double) audio_samplerate / laudio_samplerate; >- src_data.data_in = src_in; >- src_data.data_out = src_out; >- src_data.output_frames = 16384*6; >- need_resampler = true; >- } >- > if (needs_upmix) > { >- VERBOSE(VB_AUDIO, LOC + QString("create upmixer")); > if (configured_audio_channels == 6) > { > surround_mode = gContext->GetNumSetting("AudioUpmixType", 2); >@@ -351,64 +347,14 @@ > (FreeSurround::SurroundMode)surround_mode); > > VERBOSE(VB_AUDIO, LOC + >- QString("create upmixer done with surround mode %1") >+ QString("Create upmixer done with surround mode %1") > .arg(surround_mode)); > } > > VERBOSE(VB_AUDIO, LOC + QString("Audio Stretch Factor: %1") > .arg(audio_stretchfactor)); >- VERBOSE(VB_AUDIO, QString("Audio Codec Used: %1") >- .arg((audio_codec) ? >- codec_id_string(audio_codec->codec_id) : "not set")); > >- if (redo_stretch) >- { >- float laudio_stretchfactor = audio_stretchfactor; >- delete pSoundStretch; >- pSoundStretch = NULL; >- audio_stretchfactor = 0.0f; >- SetStretchFactorLocked(laudio_stretchfactor); >- } >- else >- { >- SetStretchFactorLocked(audio_stretchfactor); >- if (pSoundStretch) >- { >- // if its passthru then we need to reencode >- if (audio_codec) >- { >- if (!encoder) >- { >- VERBOSE(VB_AUDIO, LOC + >- QString("Creating Encoder for codec %1") >- .arg(audio_codec->codec_id)); >- >- encoder = new AudioOutputDigitalEncoder(); >- if (!encoder->Init(audio_codec->codec_id, >- audio_codec->bit_rate, >- audio_codec->sample_rate, >- audio_codec->channels >- )) >- { >- // eeks >- delete encoder; >- encoder = NULL; >- VERBOSE(VB_AUDIO, LOC + "Failed to Create Encoder"); >- } >- } >- } >- if (audio_codec && encoder) >- { >- pSoundStretch->setSampleRate(audio_codec->sample_rate); >- pSoundStretch->setChannels(audio_codec->channels); >- } >- else >- { >- pSoundStretch->setSampleRate(audio_samplerate); >- pSoundStretch->setChannels(audio_channels); >- } >- } >- } >+ SetStretchFactorLocked(old_audio_stretchfactor); > > // Setup visualisations, zero the visualisations buffers > prepareVisuals(); >@@ -455,10 +401,16 @@ > VERBOSE(VB_AUDIO, LOC + "Killing AudioOutputDSP"); > killaudio = true; > StopOutputThread(); >+ >+ pthread_mutex_lock(&audio_buflock); > > // Close resampler? > if (src_ctx) >+ { > src_delete(src_ctx); >+ src_ctx = NULL; >+ } >+ > need_resampler = false; > > // close sound stretcher >@@ -466,6 +418,8 @@ > { > delete pSoundStretch; > pSoundStretch = NULL; >+ old_audio_stretchfactor = audio_stretchfactor; >+ audio_stretchfactor = 1.0; > } > > if (encoder) >@@ -480,9 +434,11 @@ > upmixer = NULL; > } > needs_upmix = false; >+ audio_enc = false; > > CloseDevice(); > >+ pthread_mutex_unlock(&audio_buflock); > killAudioLock.unlock(); > } > >@@ -591,7 +547,6 @@ > ret += (now.tv_usec - audiotime_updated.tv_usec) / 1000; > ret = (long long)(ret * audio_stretchfactor); > >-#if 1 > VERBOSE(VB_AUDIO|VB_TIMESTAMP, > QString("GetAudiotime now=%1.%2, set=%3.%4, ret=%5, audt=%6 sf=%7") > .arg(now.tv_sec).arg(now.tv_usec) >@@ -600,7 +555,6 @@ > .arg(audiotime) > .arg(audio_stretchfactor) > ); >-#endif > > ret += audiotime; > >@@ -638,29 +592,23 @@ > > soundcard_buffer = getBufferedOnSoundcard(); // bytes > totalbuffer = audiolen(false) + soundcard_buffer; >- >+ > // include algorithmic latencies > if (pSoundStretch) >- { >- // add the effect of any unused but processed samples, >- // AC3 reencode does this >- totalbuffer += (int)(pSoundStretch->numSamples() * >- audio_bytes_per_sample); >- // add the effect of unprocessed samples in time stretch algo > totalbuffer += (int)((pSoundStretch->numUnprocessedSamples() * > audio_bytes_per_sample) / audio_stretchfactor); >- } > > if (upmixer && needs_upmix) >- { > totalbuffer += upmixer->sampleLatency() * audio_bytes_per_sample; >- } >+ >+ if (encoder) >+ totalbuffer += encoder->Buffered(); > > audiotime = audbuf_timecode - (int)(totalbuffer * 100000.0 / > (audio_bytes_per_sample * effdspstretched)); > > gettimeofday(&audiotime_updated, NULL); >-#if 1 >+ > VERBOSE(VB_AUDIO|VB_TIMESTAMP, > QString("SetAudiotime set=%1.%2, audt=%3 atc=%4 " > "tb=%5 sb=%6 eds=%7 abps=%8 sf=%9") >@@ -672,7 +620,6 @@ > .arg(effdspstretched) > .arg(audio_bytes_per_sample) > .arg(audio_stretchfactor)); >-#endif > > pthread_mutex_unlock(&avsync_lock); > pthread_mutex_unlock(&audio_buflock); >@@ -686,7 +633,7 @@ > int abps = (encoder) ? > encoder->audio_bytes_per_sample : audio_bytes_per_sample; > int len = samples * abps; >- >+ > // Check we have enough space to write the data > if (need_resampler && src_ctx) > len = (int)ceilf(float(len) * src_data.src_ratio); >@@ -708,6 +655,8 @@ > > return false; // would overflow > } >+ >+ pthread_mutex_lock(&audio_buflock); > > // resample input if necessary > if (need_resampler && src_ctx) >@@ -741,6 +690,8 @@ > // Call our function to do the work > _AddSamples(buffers, false, samples, timecode); > } >+ >+ pthread_mutex_unlock(&audio_buflock); > > return true; > } >@@ -753,6 +704,10 @@ > int abps = (encoder) ? > encoder->audio_bytes_per_sample : audio_bytes_per_sample; > int len = samples * abps; >+ >+ // Give original samples to mythmusic visualisation >+ dispatchVisual((unsigned char *)buffer, len, timecode, >+ source_audio_channels, audio_bits); > > // Check we have enough space to write the data > if (need_resampler && src_ctx) >@@ -776,6 +731,8 @@ > .arg(timecode)); > return false; // would overflow > } >+ >+ pthread_mutex_lock(&audio_buflock); > > // resample input if necessary > if (need_resampler && src_ctx) >@@ -804,6 +761,8 @@ > // Call our function to do the work > _AddSamples(buffer, true, samples, timecode); > } >+ >+ pthread_mutex_unlock(&audio_buflock); > > return true; > } >@@ -836,10 +795,13 @@ > if (src_ctx) > { > int error = src_reset(src_ctx); >- if (error) >+ if (error) >+ { > VERBOSE(VB_IMPORTANT, LOC_ERR + QString( > "Error occured while resetting resampler: %1") > .arg(src_strerror(error))); >+ src_ctx = NULL; >+ } > } > } > } >@@ -849,8 +811,6 @@ > void AudioOutputBase::_AddSamples(void *buffer, bool interleaved, int samples, > long long timecode) > { >- pthread_mutex_lock(&audio_buflock); >- > int len; // = samples * audio_bytes_per_sample; > int audio_bytes = audio_bits / 8; > int org_waud = waud; >@@ -867,17 +827,17 @@ > .arg(samples * abps) > .arg(AUDBUFSIZE-afree).arg(afree).arg(timecode) > .arg(needs_upmix)); >+ >+ len = WaitForFreeSpace(samples); > > if (upmixer && needs_upmix) > { > int out_samples = 0; >+ org_waud = waud; > int step = (interleaved)?source_audio_channels:1; >- len = WaitForFreeSpace(samples); // test >+ > for (int itemp = 0; itemp < samples; ) > { >- // just in case it does a processing cycle, release the lock >- // to allow the output loop to do output >- pthread_mutex_unlock(&audio_buflock); > if (audio_bytes == 2) > { > itemp += upmixer->putSamples( >@@ -894,7 +854,6 @@ > source_audio_channels, > (interleaved) ? 0 : samples); > } >- pthread_mutex_lock(&audio_buflock); > > int copy_samples = upmixer->numSamples(); > if (copy_samples) >@@ -913,10 +872,9 @@ > (short*)(audiobuffer), (copy_samples - bdiff_samples)); > } > else >- { > upmixer->receiveSamples( > (short*)(audiobuffer + org_waud), copy_samples); >- } >+ > org_waud = (org_waud + copy_len) % AUDBUFSIZE; > } > } >@@ -928,8 +886,6 @@ > } > else > { >- len = WaitForFreeSpace(samples); >- > if (interleaved) > { > char *mybuf = (char*)buffer; >@@ -964,138 +920,105 @@ > } > } > } >- >- if (samples > 0) >+ >+ if (samples <= 0) >+ return; >+ >+ if (pSoundStretch) > { >- if (pSoundStretch) >- { >- >- // does not change the timecode, only the number of samples >- // back to orig pos >- org_waud = waud; >- int bdiff = AUDBUFSIZE - org_waud; >- int nSamplesToEnd = bdiff/abps; >- if (bdiff < len) >- { >- pSoundStretch->putSamples((soundtouch::SAMPLETYPE*) >- (audiobuffer + >- org_waud), nSamplesToEnd); >- pSoundStretch->putSamples((soundtouch::SAMPLETYPE*)audiobuffer, >- (len - bdiff) / abps); >- } >- else >- { >- pSoundStretch->putSamples((soundtouch::SAMPLETYPE*) >- (audiobuffer + org_waud), >- len / abps); >- } >- >- if (encoder) >- { >- // pull out a packet's worth and reencode it until we >- // don't have enough for any more packets >- soundtouch::SAMPLETYPE *temp_buff = >- (soundtouch::SAMPLETYPE*)encoder->GetFrameBuffer(); >- size_t frameSize = encoder->FrameSize()/abps; >- >- VERBOSE(VB_AUDIO|VB_TIMESTAMP, >- QString("_AddSamples Enc sfs=%1 bfs=%2 sss=%3") >- .arg(frameSize) >- .arg(encoder->FrameSize()) >- .arg(pSoundStretch->numSamples())); >- >- // process the same number of samples as it creates >- // a full encoded buffer just like before >- while (pSoundStretch->numSamples() >= frameSize) >- { >- int got = pSoundStretch->receiveSamples( >- temp_buff, frameSize); >- int amount = encoder->Encode(temp_buff); >- >- VERBOSE(VB_AUDIO|VB_TIMESTAMP, >- QString("_AddSamples Enc bytes=%1 got=%2 left=%3") >- .arg(amount) >- .arg(got) >- .arg(pSoundStretch->numSamples())); >- >- if (!amount) >- continue; >- >- //len = WaitForFreeSpace(amount); >- char *ob = encoder->GetOutBuff(); >- if (amount >= bdiff) >- { >- memcpy(audiobuffer + org_waud, ob, bdiff); >- ob += bdiff; >- amount -= bdiff; >- org_waud = 0; >- } >- if (amount > 0) >- memcpy(audiobuffer + org_waud, ob, amount); >+ // does not change the timecode, only the number of samples >+ // back to orig pos >+ org_waud = waud; >+ int bdiff = AUDBUFSIZE - org_waud; >+ int nSamplesToEnd = bdiff/abps; >+ if (bdiff < len) >+ { >+ pSoundStretch->putSamples((soundtouch::SAMPLETYPE*) >+ (audiobuffer + >+ org_waud), nSamplesToEnd); >+ pSoundStretch->putSamples((soundtouch::SAMPLETYPE*)audiobuffer, >+ (len - bdiff) / abps); >+ } >+ else >+ pSoundStretch->putSamples((soundtouch::SAMPLETYPE*) >+ (audiobuffer + org_waud), >+ len / abps); > >- bdiff = AUDBUFSIZE - amount; >- org_waud += amount; >- } >- } >- else >- { >- int newLen = 0; >- int nSamples; >- len = WaitForFreeSpace(pSoundStretch->numSamples() * >- audio_bytes_per_sample); >- do >- { >- int samplesToGet = len/audio_bytes_per_sample; >- if (samplesToGet > nSamplesToEnd) >- { >- samplesToGet = nSamplesToEnd; >- } >- >- nSamples = pSoundStretch->receiveSamples( >- (soundtouch::SAMPLETYPE*) >- (audiobuffer + org_waud), samplesToGet); >- if (nSamples == nSamplesToEnd) >- { >- org_waud = 0; >- nSamplesToEnd = AUDBUFSIZE/audio_bytes_per_sample; >- } >- else >- { >- org_waud += nSamples * audio_bytes_per_sample; >- nSamplesToEnd -= nSamples; >- } >- >- newLen += nSamples * audio_bytes_per_sample; >- len -= nSamples * audio_bytes_per_sample; >- } while (nSamples > 0); >+ int nSamples = pSoundStretch->numSamples(); >+ len = WaitForFreeSpace(nSamples); >+ >+ while ((nSamples = pSoundStretch->numSamples())) >+ { >+ if (nSamples > nSamplesToEnd) >+ nSamples = nSamplesToEnd; >+ >+ nSamples = pSoundStretch->receiveSamples( >+ (soundtouch::SAMPLETYPE*) >+ (audiobuffer + org_waud), nSamples >+ ); >+ >+ if (nSamples == nSamplesToEnd) { >+ org_waud = 0; >+ nSamplesToEnd = AUDBUFSIZE/abps; >+ } >+ else { >+ org_waud += nSamples * abps; >+ nSamplesToEnd -= nSamples; > } >+ > } >+ >+ } > >- waud = org_waud; >- lastaudiolen = audiolen(false); >+ // Encode to AC-3? >+ if (encoder) >+ { >+ >+ org_waud = waud; >+ int bdiff = AUDBUFSIZE - org_waud; >+ int to_get = 0; > >- if (timecode < 0) >+ if (bdiff < len) > { >- // mythmusic doesn't give timestamps.. >- timecode = (int)((samples_buffered * 100000.0) / effdsp); >+ encoder->Encode(audiobuffer + org_waud, bdiff); >+ to_get = encoder->Encode(audiobuffer, len - bdiff); > } >+ else >+ to_get = encoder->Encode(audiobuffer + org_waud, len); > >- samples_buffered += samples; >- >- /* we want the time at the end -- but the file format stores >- time at the start of the chunk. */ >- // even with timestretch, timecode is still calculated from original >- // sample count >- audbuf_timecode = timecode + (int)((samples * 100000.0) / effdsp); >- >- if (interleaved) >+ if (to_get > 0) > { >- dispatchVisual((unsigned char *)buffer, len, timecode, >- source_audio_channels, audio_bits); >+ >+ if (to_get >= bdiff) >+ { >+ encoder->GetFrames(audiobuffer + org_waud, bdiff); >+ to_get -= bdiff; >+ org_waud = 0; >+ } >+ if (to_get > 0) >+ encoder->GetFrames(audiobuffer + org_waud, to_get); >+ >+ org_waud += to_get; >+ > } >+ > } > >- pthread_mutex_unlock(&audio_buflock); >+ waud = org_waud; >+ lastaudiolen = audiolen(false); >+ >+ if (timecode < 0) >+ // mythmusic doesn't give timestamps.. >+ timecode = (int)((samples_buffered * 100000.0) / effdsp); >+ >+ samples_buffered += samples; >+ >+ /* we want the time at the end -- but the file format stores >+ time at the start of the chunk. */ >+ // even with timestretch, timecode is still calculated from original >+ // sample count >+ audbuf_timecode = timecode + (int)((samples * 100000.0) / effdsp); >+ > } > > void AudioOutputBase::Status() >diff -Naur --exclude=.svn a/libs/libmyth/audiooutputbase.h b/libs/libmyth/audiooutputbase.h >--- a/libs/libmyth/audiooutputbase.h 2009-01-22 12:22:24.000000000 +1100 >+++ b/libs/libmyth/audiooutputbase.h 2009-01-28 15:49:56.000000000 +1100 >@@ -48,8 +48,7 @@ > virtual void Reconfigure(int audio_bits, > int audio_channels, > int audio_samplerate, >- bool audio_passthru, >- void *audio_codec = NULL); >+ bool audio_passthru); > > // do AddSamples calls block? > virtual void SetBlocking(bool blocking); >@@ -59,6 +58,7 @@ > > virtual void SetStretchFactor(float factor); > virtual float GetStretchFactor(void); >+ virtual bool ToggleUpmix(void); > > virtual void Reset(void); > >@@ -139,9 +139,10 @@ > QString audio_passthru_device; > > bool audio_passthru; >+ bool audio_enc; >+ bool audio_reenc; > > float audio_stretchfactor; >- AVCodecContext *audio_codec; > AudioOutputSource source; > > bool killaudio; >@@ -151,6 +152,8 @@ > bool buffer_output_data_for_use; // used by AudioOutputNULL > > int configured_audio_channels; >+ int orig_config_channels; >+ int src_quality; > > private: > // resampler >@@ -167,9 +170,12 @@ > FreeSurround *upmixer; > > int source_audio_channels; >+ int source_audio_samplerate; > int source_audio_bytes_per_sample; > bool needs_upmix; > int surround_mode; >+ bool allow_ac3_passthru; >+ float old_audio_stretchfactor; > > bool blocking; // do AddSamples calls block? > >diff -Naur --exclude=.svn a/libs/libmyth/audiooutputdigitalencoder.cpp b/libs/libmyth/audiooutputdigitalencoder.cpp >--- a/libs/libmyth/audiooutputdigitalencoder.cpp 2009-01-22 12:22:24.000000000 +1100 >+++ b/libs/libmyth/audiooutputdigitalencoder.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -27,10 +27,10 @@ > > AudioOutputDigitalEncoder::AudioOutputDigitalEncoder(void) : > av_context(NULL), >- outbuf(NULL), >- outbuf_size(0), >- frame_buffer(NULL), >- one_frame_bytes(0) >+ outbuflen(0), >+ inbuflen(0), >+ one_frame_bytes(0), >+ reorder(true) > { > } > >@@ -47,36 +47,27 @@ > av_free(av_context); > av_context = NULL; > } >- >- if (outbuf) >- { >- delete [] outbuf; >- outbuf = NULL; >- outbuf_size = 0; >- } >- >- if (frame_buffer) >- { >- delete [] frame_buffer; >- frame_buffer = NULL; >- one_frame_bytes = 0; >- } > } > > //CODEC_ID_AC3 > bool AudioOutputDigitalEncoder::Init( >- CodecID codec_id, int bitrate, int samplerate, int channels) >+ CodecID codec_id, int bitrate, int samplerate, int channels, bool reencoding) > { > AVCodec *codec; > int ret; > >- VERBOSE(VB_AUDIO, LOC + QString("Init codecid=%1, br=%2, sr=%3, ch=%4") >+ VERBOSE(VB_AUDIO, LOC + QString("Init codecid=%1, br=%2, sr=%3, ch=%4 re=%5") > .arg(codec_id_string(codec_id)) > .arg(bitrate) > .arg(samplerate) >- .arg(channels)); >- >- //codec = avcodec_find_encoder(codec_id); >+ .arg(channels) >+ .arg(reencoding)); >+ >+ reorder = !reencoding; >+ >+ // We need to do this when called from mythmusic >+ avcodec_init(); >+ avcodec_register_all(); > // always AC3 as there is no DTS encoder at the moment 2005/1/9 > codec = avcodec_find_encoder(CODEC_ID_AC3); > if (!codec) >@@ -105,8 +96,6 @@ > audio_bytes_per_sample = bytes_per_frame; > one_frame_bytes = bytes_per_frame * av_context->frame_size; > >- outbuf_size = 16384; // ok for AC3 but DTS? >- outbuf = new char [outbuf_size]; > VERBOSE(VB_AUDIO, QString("DigitalEncoder::Init fs=%1, bpf=%2 ofb=%3") > .arg(av_context->frame_size) > .arg(bytes_per_frame) >@@ -256,12 +245,26 @@ > > } AESHeader; > >+ >+void reorder_6ch_ac3(void *buf, unsigned int len) { >+ unsigned short *src = (unsigned short *)buf; >+ unsigned short tmp; >+ unsigned int samples = len >> 1; >+ >+ for (uint i = 0; i < samples; i += 6) { >+ tmp = src[i+4]; >+ src[i+4] = src[i+3]; >+ src[i+3] = src[i+2]; >+ src[i+2] = src[i+1]; >+ src[i+1] = tmp; >+ } >+} >+ > static int encode_frame( > bool dts, > unsigned char *data, >- size_t &len) >+ size_t enc_len) > { >- size_t enc_len; > int flags, sample_rate, bit_rate; > > // we don't do any length/crc validation of the AC3 frame here; presumably >@@ -273,6 +276,7 @@ > // anything with a bad CRC... > > uint nr_samples = 0, block_len; >+ > if (dts) > { > enc_len = dts_syncinfo(data+8, &flags, &sample_rate, &bit_rate); >@@ -293,15 +297,8 @@ > #endif > } > >- if (enc_len == 0 || enc_len > len) >- { >- int l = len; >- len = 0; >- return l; >- } >- > enc_len = min((uint)enc_len, block_len - 8); >- >+ > //uint32_t x = *(uint32_t*)(data+8); > // in place swab > swab((const char *)data + 8, (char *)data + 8, enc_len); >@@ -348,35 +345,49 @@ > break; > } > } >- data[5] = 0x00; >+ data[5] = 0; > data[6] = (enc_len << 3) & 0xFF; > data[7] = (enc_len >> 5) & 0xFF; > memset(data + 8 + enc_len, 0, block_len - 8 - enc_len); >- len = block_len; > > return enc_len; > } > >-// must have exactly 1 frames worth of data >-size_t AudioOutputDigitalEncoder::Encode(short *buff) >+size_t AudioOutputDigitalEncoder::Encode(void *buf, int len) > { >- int encsize = 0; > size_t outsize = 0; > >- // put data in the correct spot for encode frame >- outsize = avcodec_encode_audio( >- av_context, ((uchar*)outbuf) + 8, outbuf_size - 8, buff); >- >- size_t tmpsize = outsize; >- >- outsize = MAX_AC3_FRAME_SIZE; >- encsize = encode_frame( >- /*av_context->codec_id==CODEC_ID_DTS*/ false, >- (unsigned char*)outbuf, outsize); >- >- VERBOSE(VB_AUDIO|VB_TIMESTAMP, >- QString("DigitalEncoder::Encode len1=%1 len2=%2 finallen=%3") >- .arg(tmpsize).arg(encsize).arg(outsize)); >+ int fs = FrameSize(); >+ memcpy(inbuf+inbuflen, buf, len); >+ inbuflen += len; >+ int frames = inbuflen / fs; >+ >+ while (frames--) >+ { >+ if (reorder) >+ reorder_6ch_ac3(inbuf, fs); >+ >+ // put data in the correct spot for encode frame >+ outsize = avcodec_encode_audio( >+ av_context, ((uchar*)outbuf) + outbuflen + 8, OUTBUFSIZE - 8, (short int *)inbuf); >+ >+ encode_frame( >+ /*av_context->codec_id==CODEC_ID_DTS*/ false, >+ (unsigned char*)outbuf + outbuflen, outsize >+ ); >+ >+ outbuflen += MAX_AC3_FRAME_SIZE; >+ inbuflen -= fs; >+ memmove(inbuf, inbuf+fs, inbuflen); >+ } >+ >+ return outbuflen; >+} > >- return outsize; >+void AudioOutputDigitalEncoder::GetFrames(void *ptr, int maxlen) >+{ >+ int len = (maxlen < outbuflen ? maxlen : outbuflen); >+ memcpy(ptr, outbuf, len); >+ outbuflen -= len; >+ memmove(outbuf, outbuf+len, outbuflen); > } >diff -Naur --exclude=.svn a/libs/libmyth/audiooutputdigitalencoder.h b/libs/libmyth/audiooutputdigitalencoder.h >--- a/libs/libmyth/audiooutputdigitalencoder.h 2009-01-22 12:22:24.000000000 +1100 >+++ b/libs/libmyth/audiooutputdigitalencoder.h 2009-01-28 15:49:56.000000000 +1100 >@@ -5,37 +5,34 @@ > #include "libavcodec/avcodec.h" > }; > >+#define INBUFSIZE 131072 >+#define OUTBUFSIZE 98304 >+ > class AudioOutputDigitalEncoder > { > public: > AudioOutputDigitalEncoder(void); > ~AudioOutputDigitalEncoder(); > >- bool Init(CodecID codec_id, int bitrate, int samplerate, int channels); >+ bool Init(CodecID codec_id, int bitrate, int samplerate, >+ int channels, bool reencoding); > void Dispose(void); >- size_t Encode(short * buff); >- >- inline char *GetFrameBuffer(void); >+ size_t Encode(void *buf, int len); >+ void GetFrames(void *ptr, int maxlen); > size_t FrameSize(void) const { return one_frame_bytes; } >- char *GetOutBuff(void) const { return outbuf; } >+ int Buffered(void) const { return inbuflen; } > > public: > size_t audio_bytes_per_sample; > > private: > AVCodecContext *av_context; >- char *outbuf; >- int outbuf_size; >- char *frame_buffer; >+ char outbuf[OUTBUFSIZE]; >+ char inbuf[INBUFSIZE]; >+ int outbuflen; >+ int inbuflen; > size_t one_frame_bytes; >+ bool reorder; > }; > >-inline char *AudioOutputDigitalEncoder::GetFrameBuffer(void) >-{ >- if (!frame_buffer && av_context) >- frame_buffer = new char [one_frame_bytes]; >- >- return frame_buffer; >-} >- > #endif >diff -Naur --exclude=.svn a/libs/libmythfreesurround/el_processor.cpp b/libs/libmythfreesurround/el_processor.cpp >--- a/libs/libmythfreesurround/el_processor.cpp 2009-01-22 12:22:25.000000000 +1100 >+++ b/libs/libmythfreesurround/el_processor.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -40,17 +40,7 @@ > > const float PI = 3.141592654; > const float epsilon = 0.000001; >-//const float center_level = 0.5*sqrt(0.5); // gain of the center channel >-//const float center_level = sqrt(0.5); // gain of the center channel >-const float center_level = 1.0; // gain of the center channel >-//const float center_level = 0.5; // gain of the center channel >- >-// should be .6-.7 >-// but with centerlevel 2x what its supposed to be, we halve 0.68 >-// to keep center from clipping >-//const float window_gain = 0.34; >-//const float window_gain = 0.68; >-const float window_gain = 0.95; // to prive a bit of margin >+const float center_level = 0.5*sqrt(0.5); > > // private implementation of the surround decoder > class decoder_impl { >@@ -98,19 +88,11 @@ > outbuf[c].resize(N); > filter[c].resize(N); > } >- // DC component of filters is always 0 >- for (unsigned c=0;c<5;c++) >- { >- filter[c][0] = 0.0; >- filter[c][1] = 0.0; >- filter[c][halfN] = 0.0; >- } > sample_rate(48000); > // generate the window function (square root of hann, b/c it is applied before and after the transform) > wnd.resize(N); >- // dft normalization included in the window for zero cost scaling >- // also add a gain factor of *2 due to processing gain in algo (see center_level) >- surround_gain(1.0); >+ for (unsigned k=0;k<N;k++) >+ wnd[k] = sqrt(0.5*(1-cos(2*PI*k/N))/N); > current_buf = 0; > // set the default coefficients > surround_coefficients(0.8165,0.5774); >@@ -192,10 +174,10 @@ > // set lfe filter params > void sample_rate(unsigned int srate) { > // lfe filter is just straight through band limited >- unsigned int cutoff = (250*N)/srate; >+ unsigned int cutoff = (30*N)/srate; > for (unsigned f=0;f<=halfN;f++) { >- if ((f>=2) && (f<cutoff)) >- filter[5][f] = 1.0; >+ if (f<cutoff) >+ filter[5][f] = 0.5*sqrt(0.5); > else > filter[5][f] = 0.0; > } >@@ -214,12 +196,6 @@ > E = (o+v)*n; F = (o+u)*n; G = (o-v)*n; H = (o-u)*n; > } > >- void surround_gain(float gain) { >- master_gain = gain * window_gain * 0.5 * 0.25; >- for (unsigned k=0;k<N;k++) >- wnd[k] = sqrt(master_gain*(1-cos(2*PI*k/N))/N); >- } >- > // set the phase shifting mode > void phase_mode(unsigned mode) { > const float modes[4][2] = {{0,0},{0,PI},{PI,0},{-PI/2,PI/2}}; >@@ -290,7 +266,7 @@ > > // 2. compare amplitude and phase of each DFT bin and produce the X/Y coordinates in the sound field > // but dont do DC or N/2 component >- for (unsigned f=2;f<halfN;f++) { >+ for (unsigned f=0;f<halfN;f++) { > // get left/right amplitudes/phases > float ampL = amplitude(dftL[f]), ampR = amplitude(dftR[f]); > float phaseL = phase(dftL[f]), phaseR = phase(dftR[f]); >@@ -305,41 +281,6 @@ > phaseDiff = abs(phaseDiff); > > if (linear_steering) { >-/* cfloat w = polar(sqrt(ampL*ampL+ampR*ampR), (phaseL+phaseR)/2); >- cfloat lt = cfloat(dftL[f][0],dftL[f][1])/w, rt = cfloat(dftR[f][0],dftR[f][1])/w; */ >-// xfs[f] = -(C*(rt-H) - B*E + F*A + G*(D-lt)) / (G*A - C*E).real(); >-// yfs[f] = (rt - (xfs[f]*E+H))/(F+xfs[f]*G); >- >- /* >- Problem: >- This assumes that the values are interpolated linearly between the cardinal points. >- But this way we have no chance of knowing the average volume... >- - Can we solve that computing everything under the assumption of normalized volume? >- No. Seemingly not. >- - Maybe we should add w explitcitly into the equation and see if we can solve it... >- */ >- >- >- //cfloat lt(0.5,0),rt(0.5,0); >- //cfloat x(0,0), y(1,0); >- /*cfloat p = (C*(rt-H) - B*E + F*A + G*(D-lt)) / (G*A - C*E); >- cfloat q = B*(rt+H) + F*(D-lt) / (G*A - C*E); >- cfloat s = sqrt(p*p/4.0f - q); >- cfloat x = -p; >- cfloat x1 = -p/2.0f + s; >- cfloat x2 = -p/2.0f - s; >- float x = 0; >- if (x1.real() >= -1 && x1.real() <= 1) >- x = x1.real(); >- else if (x2.real() >= -1 && x2.real() <= 1) >- x = x2.real();*/ >- >- //cfloat yp = (rt - (x*E+H))/(F+x*G); >- //cfloat xp = (lt - (y*B+D))/(A+y*C); >- >- /*xfs[f] = x; >- yfs[f] = y.real();*/ >- > // --- this is the fancy new linear mode --- > > // get sound field x/y position >@@ -597,7 +538,6 @@ > float surround_high,surround_low; // high and low surround mixing coefficient (e.g. 0.8165/0.5774) > float surround_balance; // the xfs balance that follows from the coeffs > float surround_level; // gain for the surround channels (follows from the coeffs >- float master_gain; // gain for all channels > float phase_offsetL, phase_offsetR;// phase shifts to be applied to the rear channels > float front_separation; // front stereo separation > float rear_separation; // rear stereo separation >@@ -625,8 +565,6 @@ > > void fsurround_decoder::surround_coefficients(float a, float b) { impl->surround_coefficients(a,b); } > >-void fsurround_decoder::gain(float gain) { impl->surround_gain(gain); } >- > void fsurround_decoder::phase_mode(unsigned mode) { impl->phase_mode(mode); } > > void fsurround_decoder::steering_mode(bool mode) { impl->steering_mode(mode); } >diff -Naur --exclude=.svn a/libs/libmythfreesurround/el_processor.h b/libs/libmythfreesurround/el_processor.h >--- a/libs/libmythfreesurround/el_processor.h 2009-01-22 12:22:25.000000000 +1100 >+++ b/libs/libmythfreesurround/el_processor.h 2009-01-28 15:49:56.000000000 +1100 >@@ -47,9 +47,6 @@ > // a is the coefficient of left rear in left total, b is the coefficient of left rear in right total; the same is true for right. > void surround_coefficients(float a, float b); > >- // override for master surround gain >- void gain(float gain); >- > // set the phase shifting mode for decoding > // 0 = (+0°,+0°) - music mode > // 1 = (+0°,+180°) - PowerDVD compatibility >diff -Naur --exclude=.svn a/libs/libmythfreesurround/freesurround.cpp b/libs/libmythfreesurround/freesurround.cpp >--- a/libs/libmythfreesurround/freesurround.cpp 2009-01-22 12:22:25.000000000 +1100 >+++ b/libs/libmythfreesurround/freesurround.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -63,10 +63,9 @@ > const unsigned default_block_size = 8192; > // there will be a slider for this in the future > //const float master_gain = 1.0; >-//#define MASTER_GAIN * master_gain >+//#define MASTER_GAIN * master_gain > #define MASTER_GAIN >-//const float master_gain = 1.0/(1<<15); >-//const float inv_master_gain = (1<<15); >+//const float inv_master_gain = 1.0; > //#define INV_MASTER_GAIN * inv_master_gain > #define INV_MASTER_GAIN > >@@ -191,15 +190,13 @@ > if (moviemode) > { > params.phasemode = 1; >- params.center_width = 0; >- params.gain = 1.0; >+ params.center_width = 25; >+ params.dimension = 0.5; > } > else > { >- params.center_width = 70; >- // for 50, gain should be about 1.9, c/lr about 2.7 >- // for 70, gain should be about 3.1, c/lr about 1.5 >- params.gain = 3.1; >+ params.center_width = 65; >+ params.dimension = 0.3; > } > switch (surround_mode) > { >@@ -235,7 +232,6 @@ > decoder->phase_mode(params.phasemode); > decoder->surround_coefficients(params.coeff_a, params.coeff_b); > decoder->separation(params.front_sep/100.0,params.rear_sep/100.0); >- decoder->gain(params.gain); > } > } > >@@ -249,8 +245,7 @@ > phasemode(0), > steering(1), > front_sep(100), >- rear_sep(100), >- gain(1.0) >+ rear_sep(100) > { > } > >@@ -654,16 +649,6 @@ > { > if (decoder) > { >- // actually these params need only be set when they change... but it doesn't hurt >-#if 0 >- decoder->steering_mode(params.steering); >- decoder->phase_mode(params.phasemode); >- decoder->surround_coefficients(params.coeff_a, params.coeff_b); >- decoder->separation(params.front_sep/100.0,params.rear_sep/100.0); >-#endif >- // decode the bufs->block >- //decoder->decode(input,output,params.center_width/100.0,params.dimension/100.0); >- //decoder->decode(output,params.center_width/100.0,params.dimension/100.0); > decoder->decode(params.center_width/100.0,params.dimension/100.0); > } > } >diff -Naur --exclude=.svn a/libs/libmythsamplerate/samplerate.c b/libs/libmythsamplerate/samplerate.c >--- a/libs/libmythsamplerate/samplerate.c 2009-01-22 12:22:07.000000000 +1100 >+++ b/libs/libmythsamplerate/samplerate.c 2009-01-28 15:49:56.000000000 +1100 >@@ -452,11 +452,11 @@ > { len -- ; > > scaled_value = in [len] * (8.0 * 0x10000000) ; >- if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) >+ if (scaled_value >= (1.0 * 0x7FFFFFFF)) > { out [len] = 32767 ; > continue ; > } ; >- if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) >+ if (scaled_value <= (-8.0 * 0x10000000)) > { out [len] = -32768 ; > continue ; > } ; >diff -Naur --exclude=.svn a/libs/libmythtv/NuppelVideoPlayer.cpp b/libs/libmythtv/NuppelVideoPlayer.cpp >--- a/libs/libmythtv/NuppelVideoPlayer.cpp 2009-01-28 16:29:46.000000000 +1100 >+++ b/libs/libmythtv/NuppelVideoPlayer.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -209,7 +209,6 @@ > audio_passthru_device(QString::null), > audio_channels(2), audio_bits(-1), > audio_samplerate(44100), audio_stretchfactor(1.0f), >- audio_codec(NULL), > // Picture-in-Picture > pipplayer(NULL), setpipplayer(NULL), needsetpipplayer(false), > // Preview window support >@@ -804,8 +803,9 @@ > if (audioOutput) > { > audioOutput->Reconfigure(audio_bits, audio_channels, >- audio_samplerate, audio_passthru, >- audio_codec); >+ audio_samplerate, audio_passthru); >+ if (audio_passthru) >+ audio_channels = 2; > errMsg = audioOutput->GetError(); > if (!errMsg.isEmpty()) > audioOutput->SetStretchFactor(audio_stretchfactor); >@@ -3718,11 +3718,6 @@ > audio_passthru = passthru; > } > >-void NuppelVideoPlayer::SetAudioCodec(void *ac) >-{ >- audio_codec = ac; >-} >- > void NuppelVideoPlayer::SetEffDsp(int dsprate) > { > if (audioOutput) >diff -Naur --exclude=.svn a/libs/libmythtv/NuppelVideoPlayer.h b/libs/libmythtv/NuppelVideoPlayer.h >--- a/libs/libmythtv/NuppelVideoPlayer.h 2009-01-22 12:22:02.000000000 +1100 >+++ b/libs/libmythtv/NuppelVideoPlayer.h 2009-01-28 15:49:56.000000000 +1100 >@@ -685,7 +685,6 @@ > int audio_bits; > int audio_samplerate; > float audio_stretchfactor; >- void *audio_codec; > bool audio_passthru; > > // Picture-in-Picture >diff -Naur --exclude=.svn a/libs/libmythtv/avformatdecoder.cpp b/libs/libmythtv/avformatdecoder.cpp >--- a/libs/libmythtv/avformatdecoder.cpp 2009-01-28 16:29:46.000000000 +1100 >+++ b/libs/libmythtv/avformatdecoder.cpp 2009-01-28 16:22:52.000000000 +1100 >@@ -425,7 +425,7 @@ > audioSamples(new short int[AVCODEC_MAX_AUDIO_FRAME_SIZE]), > allow_ac3_passthru(false), allow_dts_passthru(false), > disable_passthru(false), max_channels(2), >- dummy_frame(NULL), >+ last_ac3_channels(0), dummy_frame(NULL), > // DVD > lastdvdtitle(-1), > decodeStillFrame(false), >@@ -2944,15 +2944,9 @@ > { > int idx = atracks[i].av_stream_index; > AVCodecContext *codec_ctx = ic->streams[idx]->codec; >- bool do_ac3_passthru = (allow_ac3_passthru && !transcoding && >- !disable_passthru && >- (codec_ctx->codec_id == CODEC_ID_AC3)); >- bool do_dts_passthru = (allow_dts_passthru && !transcoding && >- !disable_passthru && >- (codec_ctx->codec_id == CODEC_ID_DTS)); > AudioInfo item(codec_ctx->codec_id, > codec_ctx->sample_rate, codec_ctx->channels, >- do_ac3_passthru || do_dts_passthru); >+ DoPassThrough(codec_ctx)); > VERBOSE(VB_AUDIO, LOC + " * " + item.toString()); > } > #endif >@@ -3086,6 +3080,7 @@ > bool AvFormatDecoder::GetFrame(int onlyvideo) > { > AVPacket *pkt = NULL; >+ AC3HeaderInfo hdr; > int len; > unsigned char *ptr; > int data_size = 0; >@@ -3272,12 +3267,13 @@ > pts = 0; > > AVStream *curstream = ic->streams[pkt->stream_index]; >+ AVCodecContext *ctx = curstream->codec; > > if (pkt->dts != (int64_t)AV_NOPTS_VALUE) > pts = (long long)(av_q2d(curstream->time_base) * pkt->dts * 1000); > > if (ringBuffer->isDVD() && >- curstream->codec->codec_type == CODEC_TYPE_VIDEO) >+ ctx->codec_type == CODEC_TYPE_VIDEO) > { > MpegPreProcessPkt(curstream, pkt); > >@@ -3305,7 +3301,7 @@ > > if (!d->HasMPEG2Dec()) > { >- int current_width = curstream->codec->width; >+ int current_width = ctx->width; > int video_width = GetNVP()->GetVideoSize().width(); > if (dvd_xvmc_enabled && GetNVP() && GetNVP()->getVideoOutput()) > { >@@ -3346,7 +3342,7 @@ > } > > if (storevideoframes && >- curstream->codec->codec_type == CODEC_TYPE_VIDEO) >+ ctx->codec_type == CODEC_TYPE_VIDEO) > { > av_dup_packet(pkt); > storedPackets.append(pkt); >@@ -3354,22 +3350,21 @@ > continue; > } > >- if (len > 0 && curstream->codec->codec_type == CODEC_TYPE_VIDEO && >+ if (len > 0 && ctx->codec_type == CODEC_TYPE_VIDEO && > pkt->stream_index == selectedVideoIndex) > { >- AVCodecContext *context = curstream->codec; > >- if (context->codec_id == CODEC_ID_MPEG1VIDEO || >- context->codec_id == CODEC_ID_MPEG2VIDEO || >- context->codec_id == CODEC_ID_MPEG2VIDEO_XVMC || >- context->codec_id == CODEC_ID_MPEG2VIDEO_XVMC_VLD || >- context->codec_id == CODEC_ID_MPEGVIDEO_VDPAU) >+ if (ctx->codec_id == CODEC_ID_MPEG1VIDEO || >+ ctx->codec_id == CODEC_ID_MPEG2VIDEO || >+ ctx->codec_id == CODEC_ID_MPEG2VIDEO_XVMC || >+ ctx->codec_id == CODEC_ID_MPEG2VIDEO_XVMC_VLD || >+ ctx->codec_id == CODEC_ID_MPEGVIDEO_VDPAU) > { > if (!ringBuffer->isDVD()) > MpegPreProcessPkt(curstream, pkt); > } >- else if (context->codec_id == CODEC_ID_H264 || >- context->codec_id == CODEC_ID_H264_VDPAU) >+ else if (ctx->codec_id == CODEC_ID_H264 || >+ ctx->codec_id == CODEC_ID_H264_VDPAU) > { > H264PreProcessPkt(curstream, pkt); > } >@@ -3415,8 +3410,8 @@ > } > > if (len > 0 && >- curstream->codec->codec_type == CODEC_TYPE_DATA && >- curstream->codec->codec_id == CODEC_ID_MPEG2VBI) >+ ctx->codec_type == CODEC_TYPE_DATA && >+ ctx->codec_id == CODEC_ID_MPEG2VBI) > { > ProcessVBIDataPacket(curstream, pkt); > >@@ -3425,8 +3420,8 @@ > } > > if (len > 0 && >- curstream->codec->codec_type == CODEC_TYPE_DATA && >- curstream->codec->codec_id == CODEC_ID_DVB_VBI) >+ ctx->codec_type == CODEC_TYPE_DATA && >+ ctx->codec_id == CODEC_ID_DVB_VBI) > { > ProcessDVBDataPacket(curstream, pkt); > >@@ -3435,8 +3430,8 @@ > } > > if (len > 0 && >- curstream->codec->codec_type == CODEC_TYPE_DATA && >- curstream->codec->codec_id == CODEC_ID_DSMCC_B) >+ ctx->codec_type == CODEC_TYPE_DATA && >+ ctx->codec_id == CODEC_ID_DSMCC_B) > { > ProcessDSMCCPacket(curstream, pkt); > >@@ -3456,20 +3451,20 @@ > } > > // we don't care about other data streams >- if (curstream->codec->codec_type == CODEC_TYPE_DATA) >+ if (ctx->codec_type == CODEC_TYPE_DATA) > { > av_free_packet(pkt); > continue; > } > >- if (!curstream->codec->codec) >+ if (!ctx->codec) > { > VERBOSE(VB_PLAYBACK, LOC + > QString("No codec for stream index %1, type(%2) id(%3:%4)") > .arg(pkt->stream_index) >- .arg(codec_type_string(curstream->codec->codec_type)) >- .arg(codec_id_string(curstream->codec->codec_id)) >- .arg(curstream->codec->codec_id)); >+ .arg(codec_type_string(ctx->codec_type)) >+ .arg(codec_id_string(ctx->codec_id)) >+ .arg(ctx->codec_id)); > av_free_packet(pkt); > continue; > } >@@ -3478,7 +3473,7 @@ > have_err = false; > > avcodeclock.lock(); >- int ctype = curstream->codec->codec_type; >+ int ctype = ctx->codec_type; > int audIdx = selectedTrack[kTrackTypeAudio].av_stream_index; > int audSubIdx = selectedTrack[kTrackTypeAudio].av_substream_index; > int subIdx = selectedTrack[kTrackTypeSubtitle].av_stream_index; >@@ -3503,50 +3498,52 @@ > > // detect switches between stereo and dual languages > bool wasDual = audSubIdx != -1; >- bool isDual = curstream->codec->avcodec_dual_language; >+ bool isDual = ctx->avcodec_dual_language; > if ((wasDual && !isDual) || (!wasDual && isDual)) > { > SetupAudioStreamSubIndexes(audIdx); > reselectAudioTrack = true; > } > >- bool do_ac3_passthru = >- (allow_ac3_passthru && !transcoding && >- (curstream->codec->codec_id == CODEC_ID_AC3)); >- bool do_dts_passthru = >- (allow_dts_passthru && !transcoding && >- (curstream->codec->codec_id == CODEC_ID_DTS)); >- bool using_passthru = do_ac3_passthru || do_dts_passthru; >- > // detect channels on streams that need > // to be decoded before we can know this > bool already_decoded = false; >- if (!curstream->codec->channels) >+ if (!ctx->channels) > { > QMutexLocker locker(&avcodeclock); > VERBOSE(VB_IMPORTANT, LOC + > QString("Setting channels to %1") > .arg(audioOut.channels)); > >- if (using_passthru) >+ if (DoPassThrough(ctx)) > { > // for passthru let it select the max number > // of channels >- curstream->codec->channels = 0; >- curstream->codec->request_channels = 0; >+ ctx->channels = 0; >+ ctx->request_channels = 0; > } > else > { >- curstream->codec->channels = audioOut.channels; >- curstream->codec->request_channels = >+ ctx->channels = audioOut.channels; >+ ctx->request_channels = > audioOut.channels; > } > ret = avcodec_decode_audio( >- curstream->codec, audioSamples, >+ ctx, audioSamples, > &data_size, ptr, len); > already_decoded = true; > >- reselectAudioTrack |= curstream->codec->channels; >+ reselectAudioTrack |= ctx->channels; >+ } >+ >+ if (ctx->codec_id == CODEC_ID_AC3 && >+ !ff_ac3_parse_header(ptr, &hdr)) >+ { >+ if (hdr.channels != last_ac3_channels) >+ { >+ last_ac3_channels = ctx->channels = hdr.channels; >+ SetupAudioStream(); >+ } > } > > if (reselectAudioTrack) >@@ -3562,6 +3559,7 @@ > .av_stream_index; > audSubIdx = selectedTrack[kTrackTypeAudio] > .av_substream_index; >+ ctx = curstream->codec; > } > > if ((onlyvideo > 0) || (pkt->stream_index != audIdx)) >@@ -3593,14 +3591,12 @@ > if (audioOut.do_passthru) > { > data_size = pkt->size; >- bool dts = CODEC_ID_DTS == curstream->codec->codec_id; >+ bool dts = CODEC_ID_DTS == ctx->codec_id; > ret = encode_frame(dts, ptr, len, > audioSamples, data_size); > } > else > { >- AVCodecContext *ctx = curstream->codec; >- > if ((ctx->channels == 0) || > (ctx->channels > audioOut.channels)) > { >@@ -3609,8 +3605,7 @@ > > if (!already_decoded) > { >- curstream->codec->request_channels = >- audioOut.channels; >+ ctx->request_channels = audioOut.channels; > ret = avcodec_decode_audio( > ctx, audioSamples, &data_size, ptr, len); > } >@@ -3627,6 +3622,7 @@ > audIdx = -1; > AutoSelectAudioTrack(); > data_size = 0; >+ ctx = curstream->codec; > } > } > avcodeclock.unlock(); >@@ -3644,8 +3640,7 @@ > > // calc for next frame > lastapts += (long long)((double)(data_size * 1000) / >- (curstream->codec->channels * 2) / >- curstream->codec->sample_rate); >+ (ctx->channels * 2) / ctx->sample_rate); > > VERBOSE(VB_PLAYBACK|VB_TIMESTAMP, > LOC + QString("audio timecode %1 %2 %3 %4") >@@ -3705,7 +3700,6 @@ > continue; > } > >- AVCodecContext *context = curstream->codec; > AVFrame mpa_pic; > bzero(&mpa_pic, sizeof(AVFrame)); > >@@ -3720,24 +3714,24 @@ > // HACK > while (!gotpicture && count < 5) > { >- ret = d->DecodeMPEG2Video(context, &mpa_pic, >+ ret = d->DecodeMPEG2Video(ctx, &mpa_pic, > &gotpicture, ptr, len); > count++; > } > } > else > { >- ret = d->DecodeMPEG2Video(context, &mpa_pic, >+ ret = d->DecodeMPEG2Video(ctx, &mpa_pic, > &gotpicture, ptr, len); > } > } > else > { >- ret = avcodec_decode_video(context, &mpa_pic, >+ ret = avcodec_decode_video(ctx, &mpa_pic, > &gotpicture, ptr, len); > // Reparse it to not drop the DVD still frame > if (decodeStillFrame) >- ret = avcodec_decode_video(context, &mpa_pic, >+ ret = avcodec_decode_video(ctx, &mpa_pic, > &gotpicture, ptr, len); > } > avcodeclock.unlock(); >@@ -3804,9 +3798,9 @@ > > img_convert(&tmppicture, PIX_FMT_YUV420P, > (AVPicture *)&mpa_pic, >- context->pix_fmt, >- context->width, >- context->height); >+ ctx->pix_fmt, >+ ctx->width, >+ ctx->height); > > if (xf) > { >@@ -3829,10 +3823,10 @@ > (temppts + 10000 > lastvpts || temppts < 0)) > { > temppts = lastvpts; >- temppts += (long long)(1000 * av_q2d(context->time_base)); >+ temppts += (long long)(1000 * av_q2d(ctx->time_base)); > // MPEG2 frames can be repeated, update pts accordingly > temppts += (long long)(mpa_pic.repeat_pict * 500 >- * av_q2d(curstream->codec->time_base)); >+ * av_q2d(ctx->time_base)); > } > > VERBOSE(VB_PLAYBACK|VB_TIMESTAMP, LOC + >@@ -3868,7 +3862,7 @@ > picframe->frameNumber = framesPlayed; > GetNVP()->ReleaseNextVideoFrame(picframe, temppts); > if (d->HasMPEG2Dec() && mpa_pic.data[3]) >- context->release_buffer(context, &mpa_pic); >+ ctx->release_buffer(ctx, &mpa_pic); > > decoded_video_frame = picframe; > gotvideo = 1; >@@ -3927,11 +3921,10 @@ > } > default: > { >- AVCodecContext *enc = curstream->codec; > VERBOSE(VB_IMPORTANT, LOC_ERR + > QString("Decoding - id(%1) type(%2)") >- .arg(codec_id_string(enc->codec_id)) >- .arg(codec_type_string(enc->codec_type))); >+ .arg(codec_id_string(ctx->codec_id)) >+ .arg(codec_type_string(ctx->codec_type))); > have_err = true; > break; > } >@@ -4080,6 +4073,25 @@ > } > } > >+bool AvFormatDecoder::DoPassThrough(const AVCodecContext *ctx) >+{ >+ bool passthru = false; >+ >+ if (ctx->codec_id == CODEC_ID_AC3) >+ passthru = allow_ac3_passthru && >+ ctx->channels >= (int)max_channels; >+ else if (ctx->codec_id == CODEC_ID_DTS) >+ passthru = allow_dts_passthru; >+ >+ passthru &= !transcoding && !disable_passthru; >+ // Don't know any cards that support spdif clocked at < 44100 >+ // Some US cable transmissions have 2ch 32k AC-3 streams >+ passthru &= ctx->sample_rate >= 44100; >+ >+ return passthru; >+} >+ >+ > /** \fn AvFormatDecoder::SetupAudioStream(void) > * \brief Reinitializes audio if it needs to be reinitialized. > * >@@ -4093,7 +4105,6 @@ > AVStream *curstream = NULL; > AVCodecContext *codec_ctx = NULL; > AudioInfo old_in = audioIn; >- AudioInfo old_out = audioOut; > bool using_passthru = false; > > if ((currentTrack[kTrackTypeAudio] >= 0) && >@@ -4105,14 +4116,9 @@ > assert(curstream); > assert(curstream->codec); > codec_ctx = curstream->codec; >- bool do_ac3_passthru = (allow_ac3_passthru && !transcoding && >- (codec_ctx->codec_id == CODEC_ID_AC3)); >- bool do_dts_passthru = (allow_dts_passthru && !transcoding && >- (codec_ctx->codec_id == CODEC_ID_DTS)); >- using_passthru = do_ac3_passthru || do_dts_passthru; >- info = AudioInfo(codec_ctx->codec_id, >- codec_ctx->sample_rate, codec_ctx->channels, >- using_passthru && !disable_passthru); >+ using_passthru = DoPassThrough(codec_ctx); >+ info = AudioInfo(codec_ctx->codec_id, codec_ctx->sample_rate, >+ codec_ctx->channels, using_passthru); > } > > if (info == audioIn) >@@ -4123,64 +4129,26 @@ > QString("audio track #%1").arg(currentTrack[kTrackTypeAudio]+1)); > > audioOut = audioIn = info; >- if (using_passthru) >- { >- // A passthru stream looks like a 48KHz 2ch (@ 16bit) to the sound card >- AudioInfo digInfo = audioOut; >- if (!disable_passthru) >- { >- digInfo.channels = 2; >- digInfo.sample_rate = 48000; >- digInfo.sample_size = 4; >- } >- if (audioOut.channels > (int) max_channels) >- { >- audioOut.channels = (int) max_channels; >- audioOut.sample_size = audioOut.channels * 2; >- codec_ctx->channels = audioOut.channels; >- } >- VERBOSE(VB_AUDIO, LOC + "Audio format changed digital passthrough " + >- QString("%1\n\t\t\tfrom %2 ; %3\n\t\t\tto %4 ; %5") >- .arg(digInfo.toString()) >- .arg(old_in.toString()).arg(old_out.toString()) >- .arg(audioIn.toString()).arg(audioOut.toString())); >- >- if (digInfo.sample_rate > 0) >- GetNVP()->SetEffDsp(digInfo.sample_rate * 100); >- >- GetNVP()->SetAudioParams(digInfo.bps(), digInfo.channels, >- digInfo.sample_rate, audioIn.do_passthru); >- // allow the audio stuff to reencode >- GetNVP()->SetAudioCodec(codec_ctx); >- GetNVP()->ReinitAudio(); >- return true; >- } >- else >+ >+ if (!using_passthru && audioOut.channels > (int)max_channels) > { >- if (audioOut.channels > (int) max_channels) >- { >- audioOut.channels = (int) max_channels; >- audioOut.sample_size = audioOut.channels * 2; >- codec_ctx->channels = audioOut.channels; >- } >+ audioOut.channels = (int)max_channels; >+ audioOut.sample_size = audioOut.channels * 2; >+ codec_ctx->channels = audioOut.channels; > } >- >+ > VERBOSE(VB_AUDIO, LOC + "Audio format changed " + >- QString("\n\t\t\tfrom %1 ; %2\n\t\t\tto %3 ; %4") >- .arg(old_in.toString()).arg(old_out.toString()) >- .arg(audioIn.toString()).arg(audioOut.toString())); >+ QString("\n\t\t\tfrom %1 to %2") >+ .arg(old_in.toString()).arg(audioOut.toString())); > > if (audioOut.sample_rate > 0) > GetNVP()->SetEffDsp(audioOut.sample_rate * 100); > > GetNVP()->SetAudioParams(audioOut.bps(), audioOut.channels, > audioOut.sample_rate, >- audioIn.do_passthru); >+ audioOut.do_passthru); > >- // allow the audio stuff to reencode >- GetNVP()->SetAudioCodec(using_passthru?codec_ctx:NULL); > QString errMsg = GetNVP()->ReinitAudio(); >- bool audiook = errMsg.isEmpty(); > > return true; > } >diff -Naur --exclude=.svn a/libs/libmythtv/avformatdecoder.h b/libs/libmythtv/avformatdecoder.h >--- a/libs/libmythtv/avformatdecoder.h 2009-01-28 16:29:46.000000000 +1100 >+++ b/libs/libmythtv/avformatdecoder.h 2009-01-28 15:49:56.000000000 +1100 >@@ -198,6 +198,7 @@ > > void SeekReset(long long, uint skipFrames, bool doFlush, bool discardFrames); > >+ bool DoPassThrough(const AVCodecContext *ctx); > bool SetupAudioStream(void); > void SetupAudioStreamSubIndexes(int streamIndex); > void RemoveAudioStreams(); >@@ -266,6 +267,7 @@ > bool allow_dts_passthru; > bool disable_passthru; > uint max_channels; >+ uint last_ac3_channels; > > VideoFrame *dummy_frame; > >diff -Naur --exclude=.svn a/libs/libmythtv/tv_play.cpp b/libs/libmythtv/tv_play.cpp >--- a/libs/libmythtv/tv_play.cpp 2009-01-22 12:22:03.000000000 +1100 >+++ b/libs/libmythtv/tv_play.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -348,6 +348,7 @@ > REG_KEY("TV Playback", "VOLUMEDOWN", "Volume down", "[,{,F10,Volume Down"); > REG_KEY("TV Playback", "VOLUMEUP", "Volume up", "],},F11,Volume Up"); > REG_KEY("TV Playback", "MUTE", "Mute", "|,\\,F9,Volume Mute"); >+ REG_KEY("TV Playback", "TOGGLEUPMIX", "Toggle upmixer", "Ctrl+U"); > REG_KEY("TV Playback", "TOGGLEPIPMODE", "Toggle Picture-in-Picture mode", > "V"); > REG_KEY("TV Playback", "TOGGLEPIPWINDOW", "Toggle active PiP window", "B"); >@@ -480,7 +481,7 @@ > Teletext F2,F3,F4,F5,F6,F7,F8 > ITV F2,F3,F4,F5,F6,F7,F12 > >- Playback: Ctrl-B,Ctrl-G,Ctrl-Y >+ Playback: Ctrl-B,Ctrl-G,Ctrl-Y,Ctrl-U > */ > } > >@@ -2710,7 +2711,7 @@ > else if (action == "VOLUMEDOWN" || action == "VOLUMEUP" || > action == "STRETCHINC" || action == "STRETCHDEC" || > action == "MUTE" || action == "TOGGLEASPECT" || >- action == "TOGGLEFILL" ) >+ action == "TOGGLEFILL" || action == "TOGGLEUPMIX") > { > passThru = 1; > handled = false; >@@ -2725,11 +2726,11 @@ > else > handled = false; > } >- >+ > if (!passThru) > return; > } >- >+ > if (zoomMode) > { > int passThru = 0; >@@ -2765,7 +2766,7 @@ > else if (action == "VOLUMEDOWN" || action == "VOLUMEUP" || > action == "STRETCHINC" || action == "STRETCHDEC" || > action == "MUTE" || action == "PAUSE" || >- action == "CLEAROSD") >+ action == "CLEAROSD" || action == "TOGGLEUPMIX") > { > passThru = 1; > handled = false; >@@ -2777,7 +2778,7 @@ > if (!passThru) > return; > } >- >+ > if (dialogname != "" && GetOSD() && GetOSD()->DialogShowing(dialogname)) > { > for (unsigned int i = 0; i < actions.size() && !handled; i++) >@@ -3036,7 +3037,7 @@ > return; > } > } >- >+ > for (unsigned int i = 0; i < actions.size() && !handled; i++) > { > QString action = actions[i]; >@@ -3070,6 +3071,8 @@ > ChangeTimeStretch(0); // just display > else if (action == "TOGGLESTRETCH") > ToggleTimeStretch(); >+ else if (action == "TOGGLEUPMIX") >+ ToggleUpmix(); > else if (action == "CYCLECOMMSKIPMODE") { > SetAutoCommercialSkip((enum commSkipMode) > ((autoCommercialSkip + 1) % CommSkipModes)); >@@ -6054,6 +6057,22 @@ > } > } > >+void TV::ToggleUpmix() >+{ >+ AudioOutput *aud = nvp->getAudioOutput(); >+ if (!aud) >+ return; >+ QString text; >+ if (aud->ToggleUpmix()) >+ text = tr("Upmixer On"); >+ else >+ text = tr("Upmixer Off"); >+ >+ if (GetOSD() && !browsemode) >+ GetOSD()->SetSettingsText(text, 5); >+} >+ >+ > // dir in 10ms jumps > void TV::ChangeAudioSync(int dir, bool allowEdit) > { >@@ -7300,6 +7319,8 @@ > > ChangeTimeStretch(0, !floatRead); // just display > } >+ else if (action == "TOGGLEUPMIX") >+ ToggleUpmix(); > else if (action.left(11) == "SELECTSCAN_") > activenvp->SetScanType((FrameScanType) action.right(1).toInt()); > else if (action.left(15) == "TOGGLEAUDIOSYNC") >@@ -7547,6 +7568,8 @@ > subitem = new OSDGenericTree(item, tr("1.5X"), "ADJUSTSTRETCH1.5", > (speedX100 == 150) ? 1 : 0, NULL, > "STRETCHGROUP"); >+ >+ item = new OSDGenericTree(treeMenu, tr("Toggle Upmixer"), "TOGGLEUPMIX"); > > // add scan mode override settings to menu > FrameScanType scan_type = kScan_Ignore; >diff -Naur --exclude=.svn a/libs/libmythtv/tv_play.h b/libs/libmythtv/tv_play.h >--- a/libs/libmythtv/tv_play.h 2009-01-22 12:22:02.000000000 +1100 >+++ b/libs/libmythtv/tv_play.h 2009-01-28 15:49:56.000000000 +1100 >@@ -314,6 +314,7 @@ > void ChangeSpeed(int direction); > void ToggleTimeStretch(void); > void ChangeTimeStretch(int dir, bool allowEdit = true); >+ void ToggleUpmix(void); > void ChangeAudioSync(int dir, bool allowEdit = true); > float StopFFRew(void); > void ChangeFFRew(int direction); >diff -Naur --exclude=.svn a/programs/mythfrontend/globalsettings.cpp b/programs/mythfrontend/globalsettings.cpp >--- a/programs/mythfrontend/globalsettings.cpp 2009-01-22 12:22:26.000000000 +1100 >+++ b/programs/mythfrontend/globalsettings.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -116,6 +116,26 @@ > return gc; > } > >+static HostComboBox *SRCQuality() >+{ >+ HostComboBox *gc = new HostComboBox("SRCQuality", false); >+ gc->setLabel(QObject::tr("Sample Rate Conversion")); >+ gc->addSelection(QObject::tr("Best"), "3", true); // default >+ gc->addSelection(QObject::tr("Medium"), "2"); >+ gc->addSelection(QObject::tr("Fastest"), "1"); >+ gc->addSelection(QObject::tr("Disabled"), "0"); >+ gc->setHelpText( >+ QObject::tr( >+ "Set the quality of audio sample rate conversion. " >+ "This only affects non 48000Hz PCM audio. " >+ "All three options offer a worst-case SNR of 97dB. " >+ "'Best' at a bandwidth of 97%. " >+ "'Medium' at a bandwidth of 90%. " >+ "'Fastest' at a bandwidth of 80%. " >+ "Set 'Disabled' only if you know what you are doing . ")); >+ return gc; >+} >+ > static HostComboBox *PassThroughOutputDevice() > { > HostComboBox *gc = new HostComboBox("PassThruOutputDevice", true); >@@ -3307,6 +3327,11 @@ > agrp->addChild(MaxAudioChannels()); > agrp->addChild(AudioUpmixType()); > addChild(agrp); >+ >+ HorizontalConfigurationGroup *agrp1 = >+ new HorizontalConfigurationGroup(false, false, true, true); >+ agrp1->addChild(SRCQuality()); >+ addChild(agrp1); > > VerticalConfigurationGroup *vgrp1 = > new VerticalConfigurationGroup(false, false, true, true); >diff -Naur --exclude=.svn a/programs/mythtranscode/transcode.cpp b/programs/mythtranscode/transcode.cpp >--- a/programs/mythtranscode/transcode.cpp 2009-01-22 12:22:26.000000000 +1100 >+++ b/programs/mythtranscode/transcode.cpp 2009-01-28 15:49:56.000000000 +1100 >@@ -55,12 +55,10 @@ > > // reconfigure sound out for new params > virtual void Reconfigure(int audio_bits, int audio_channels, >- int audio_samplerate, bool audio_passthru, >- void *audio_codec = NULL) >+ int audio_samplerate, bool audio_passthru) > { > (void)audio_samplerate; > (void)audio_passthru; >- (void)audio_codec; > > ClearError(); > bits = audio_bits; >@@ -218,6 +216,11 @@ > // Do nothing > return MUTE_OFF; > } >+ virtual bool ToggleUpmix(void) >+ { >+ // Do nothing >+ return false; >+ } > > // These are pure virtual in AudioOutput, but we don't need them here > virtual void bufferOutputData(bool){ return; }
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 259009
:
182053
| 182055 |
182056
|
182057
|
182059
|
182060