📄 newdenoise.cc
字号:
g_pPixelsCbCr[i] = PixelCbCr (aCbCr); } } assert (i == g_nPixelsCbCr); // Pass the frame to the denoiser. g_oMotionSearcherCbCr.AddFrame (eStatus, g_pPixelsCbCr); if (eStatus != g_kNoError) return -1; } } // If we're denoising both color & intensity, make sure we // either got two reference frames or none at all. assert (!g_bMotionSearcherY || !g_bMotionSearcherCbCr || (pFrameY == NULL && pFrameCbCr == NULL) || (pFrameY != NULL && pFrameCbCr != NULL)); // Return whether there was an output frame this time. return (g_bMotionSearcherY && pFrameY != NULL || g_bMotionSearcherCbCr && pFrameCbCr != NULL) ? 0 : 1;}intnewdenoise_interlaced_frame_intensity (const uint8_t *a_pInputY, uint8_t *a_pOutputY){ Status_t eStatus; // An error that may occur. const MotionSearcherY::ReferenceFrame_t *pFrameY; // Denoised frame data, ready for output. int i, x, y; // Used to loop through pixels. int nMask; // Used to switch between top-field interlacing and bottom-field // interlacing. // Make sure intensity is being denoised. assert (g_bMotionSearcherY); // No errors yet. eStatus = g_kNoError; // No output frames have been received yet. pFrameY = NULL; // If it's time to purge, do so. { extern int frame; if (frame % denoiser.frames == 0) g_oMotionSearcherY.Purge(); } // Set up for the type of interlacing. nMask = (denoiser.interlaced == 2) ? 1 : 0; // If the end of input has been reached, then return the next // remaining denoised frame, if available. if (a_pInputY == NULL) { // Get 1/2 any remaining frame. pFrameY = g_oMotionSearcherY.GetRemainingFrames(); // Output it. output_field (nMask ^ 0, pFrameY, NULL, a_pOutputY, NULL, NULL); // Get 1/2 any remaining frame. pFrameY = g_oMotionSearcherY.GetRemainingFrames(); // Output it. output_field (nMask ^ 1, pFrameY, NULL, a_pOutputY, NULL, NULL); } // Otherwise, if there is more input, feed the frame into the // denoiser & possibly get a frame back. else { // Get 1/2 any frame that's ready for output. pFrameY = g_oMotionSearcherY.GetFrameReadyForOutput(); // Output it. output_field (nMask ^ 0, pFrameY, NULL, a_pOutputY, NULL, NULL); // Convert the input frame into the format needed by the // denoiser. for (i = 0, y = (nMask ^ 0); y < g_nHeightY; y += 2) for (x = 0; x < g_nWidthY; ++x, ++i) g_pPixelsY[i] = PixelY (a_pInputY + (y * g_nWidthY + x)); assert (i == g_nPixelsY); // Pass the frame to the denoiser. g_oMotionSearcherY.AddFrame (eStatus, g_pPixelsY); if (eStatus != g_kNoError) return -1; // Get 1/2 any frame that's ready for output. pFrameY = g_oMotionSearcherY.GetFrameReadyForOutput(); // Output it. output_field (nMask ^ 1, pFrameY, NULL, a_pOutputY, NULL, NULL); // Convert the input frame into the format needed by the // denoiser. for (i = 0, y = (nMask ^ 1); y < g_nHeightY; y += 2) for (x = 0; x < g_nWidthY; ++x, ++i) g_pPixelsY[i] = PixelY (a_pInputY + (y * g_nWidthY + x)); assert (i == g_nPixelsY); // Pass the frame to the denoiser. g_oMotionSearcherY.AddFrame (eStatus, g_pPixelsY); if (eStatus != g_kNoError) return -1; } // Return whether there was an output frame this time. return (pFrameY != NULL) ? 0 : 1;}intnewdenoise_interlaced_frame_color (const uint8_t *a_pInputCb, const uint8_t *a_pInputCr, uint8_t *a_pOutputCb, uint8_t *a_pOutputCr){ Status_t eStatus; // An error that may occur. const MotionSearcherCbCr::ReferenceFrame_t *pFrameCbCr; // Denoised frame data, ready for output. int i, x, y; // Used to loop through pixels. int nMask; // Used to switch between top-field interlacing and bottom-field // interlacing. // Make sure color is being denoised. assert (g_bMotionSearcherCbCr); // No errors yet. eStatus = g_kNoError; // No output frames have been received yet. pFrameCbCr = NULL; // If it's time to purge, do so. { extern int frame; if (frame % denoiser.frames == 0) g_oMotionSearcherCbCr.Purge(); } // Set up for the type of interlacing. nMask = (denoiser.interlaced == 2) ? 1 : 0; // If the end of input has been reached, then return the next // remaining denoised frame, if available. if (a_pInputCr == NULL) { // Get 1/2 any remaining frame. pFrameCbCr = g_oMotionSearcherCbCr.GetRemainingFrames(); // Output it. output_field (nMask ^ 0, NULL, pFrameCbCr, NULL, a_pOutputCb, a_pOutputCr); // Get 1/2 any remaining frame. pFrameCbCr = g_oMotionSearcherCbCr.GetRemainingFrames(); // Output it. output_field (nMask ^ 1, NULL, pFrameCbCr, NULL, a_pOutputCb, a_pOutputCr); } // Otherwise, if there is more input, feed the frame into the // denoiser & possibly get a frame back. else { // Get 1/2 any frame that's ready for output. pFrameCbCr = g_oMotionSearcherCbCr.GetFrameReadyForOutput(); // Output it. output_field (nMask ^ 0, NULL, pFrameCbCr, NULL, a_pOutputCb, a_pOutputCr); // Pass the input frame to the denoiser. { PixelCbCr::Num_t aCbCr[2]; // Convert the input frame into the format needed by the // denoiser. for (i = 0, y = (nMask ^ 0); y < g_nHeightCbCr; y += 2) { for (x = 0; x < g_nWidthCbCr; ++x, ++i) { aCbCr[0] = a_pInputCb[y * g_nWidthCbCr + x]; aCbCr[1] = a_pInputCr[y * g_nWidthCbCr + x]; g_pPixelsCbCr[i] = PixelCbCr (aCbCr); } } assert (i == g_nPixelsCbCr); // Pass the frame to the denoiser. g_oMotionSearcherCbCr.AddFrame (eStatus, g_pPixelsCbCr); if (eStatus != g_kNoError) return -1; } // Get 1/2 any frame that's ready for output. pFrameCbCr = g_oMotionSearcherCbCr.GetFrameReadyForOutput(); // Output it. output_field (nMask ^ 1, NULL, pFrameCbCr, NULL, a_pOutputCb, a_pOutputCr); // Pass the input frame to the denoiser. { PixelCbCr::Num_t aCbCr[2]; // Convert the input frame into the format needed by the // denoiser. for (i = 0, y = (nMask ^ 1); y < g_nHeightCbCr; y += 2) { for (x = 0; x < g_nWidthCbCr; ++x, ++i) { aCbCr[0] = a_pInputCb[y * g_nWidthCbCr + x]; aCbCr[1] = a_pInputCr[y * g_nWidthCbCr + x]; g_pPixelsCbCr[i] = PixelCbCr (aCbCr); } } assert (i == g_nPixelsCbCr); // Pass the frame to the denoiser. g_oMotionSearcherCbCr.AddFrame (eStatus, g_pPixelsCbCr); if (eStatus != g_kNoError) return -1; } } // Return whether there was an output frame this time. return (pFrameCbCr != NULL) ? 0 : 1;}intnewdenoise_interlaced_frame (const uint8_t *a_pInputY, const uint8_t *a_pInputCb, const uint8_t *a_pInputCr, uint8_t *a_pOutputY, uint8_t *a_pOutputCb, uint8_t *a_pOutputCr){ int bY, bCbCr; // Make the compiler shut up. bY = bCbCr = 0; // Denoise intensity & color. if (g_bMotionSearcherCbCr && denoiser.threads == 2) g_oDenoiserThreadCbCr.AddFrame (a_pInputCb, a_pInputCr, a_pOutputCb, a_pOutputCr); if (g_bMotionSearcherY) bY = newdenoise_interlaced_frame_intensity (a_pInputY, a_pOutputY); if (g_bMotionSearcherCbCr && denoiser.threads != 2) bCbCr = newdenoise_interlaced_frame_color (a_pInputCb, a_pInputCr, a_pOutputCb, a_pOutputCr); if (g_bMotionSearcherCbCr && denoiser.threads == 2) bCbCr = g_oDenoiserThreadCbCr.WaitForAddFrame(); // If we're denoising both color & intensity, make sure we // either got two reference frames or none at all. assert (!g_bMotionSearcherY || !g_bMotionSearcherCbCr || (bY != 0 && bCbCr != 0) || (bY == 0 && bCbCr == 0)); // Return 0 if there are no errors. return (bY) ? bY : bCbCr;}static void output_field (int a_nMask, const MotionSearcherY::ReferenceFrame_t *a_pFrameY, const MotionSearcherCbCr::ReferenceFrame_t *a_pFrameCbCr, uint8_t *a_pOutputY, uint8_t *a_pOutputCb, uint8_t *a_pOutputCr){ int i, x, y; // Used to loop through pixels. // Convert any denoised intensity frame into the format expected // by our caller. if (a_pFrameY != NULL) { ReferencePixelY *pY; // The pixel, as it's being converted to the output format. // Make sure our caller gave us somewhere to write output. assert (a_pOutputY != NULL); // Loop through all the pixels, convert them to the output // format. for (i = 0, y = a_nMask; y < g_nHeightY; y += 2) { for (x = 0; x < g_nWidthY; ++x, ++i) { pY = a_pFrameY->GetPixel (i); assert (pY != NULL); a_pOutputY[y * g_nWidthY + x] = pY->GetValue()[0]; } } } if (a_pFrameCbCr != NULL) { ReferencePixelCbCr *pCbCr; // The pixel, as it's being converted to the output format. // Make sure our caller gave us somewhere to write output. assert (a_pOutputCb != NULL && a_pOutputCr != NULL); // Loop through all the pixels, convert them to the output // format. for (i = 0, y = a_nMask; y < g_nHeightCbCr; y += 2) { for (x = 0; x < g_nWidthCbCr; ++x, ++i) { pCbCr = a_pFrameCbCr->GetPixel (i); assert (pCbCr != NULL); const PixelCbCr &rCbCr = pCbCr->GetValue(); a_pOutputCb[y * g_nWidthCbCr + x] = rCbCr[0]; a_pOutputCr[y * g_nWidthCbCr + x] = rCbCr[1]; } } }}// The ThreadMutex class.// Default constructor.ThreadMutex::ThreadMutex(){ int nErr; // An error that may occur. pthread_mutexattr_t sMutexAttr; // Attributes for the mutex.#ifndef NDEBUG // Not locked upon creation. m_bLocked = false;#endif // NDEBUG // Initialize the mutex. nErr = pthread_mutexattr_init (&sMutexAttr); if (nErr != 0) mjpeg_error_exit1 ("pthread_mutexattr_init() failed: %s", strerror (nErr)); nErr = pthread_mutex_init (&m_oMutex, &sMutexAttr); if (nErr != 0) mjpeg_error_exit1 ("pthread_mutex_init() failed: %s", strerror (nErr)); nErr = pthread_mutexattr_destroy (&sMutexAttr); if (nErr != 0) mjpeg_error_exit1 ("pthread_mutexattr_destroy() failed: %s", strerror (nErr));}// Destructor.ThreadMutex::~ThreadMutex(){ int nErr; // An error that may occur. // Make sure it's not locked. assert (!m_bLocked); // Destroy the mutex. nErr = pthread_mutex_destroy (&m_oMutex); if (nErr != 0) mjpeg_error_exit1 ("pthread_mutex_destroy() failed: %s", strerror (nErr));}// Lock the mutex.voidThreadMutex::Lock (void){ int nErr; // An error that may occur. // Get exclusive access. nErr = pthread_mutex_lock (&m_oMutex); if (nErr != 0) mjpeg_error_exit1 ("pthread_mutex_lock() failed: %s", strerror (nErr));#ifndef NDEBUG // Now it's locked. m_bLocked = true;#endif // NDEBUG}// Unlock the mutexvoidThreadMutex::Unlock (void){ int nErr; // An error that may occur. // Make sure it's locked. assert (m_bLocked);#ifndef NDEBUG // Now it's unlocked. (Another thread may lock it immediately, but // that's not our concern.) m_bLocked = false;#endif // NDEBUG // Release exclusive access. nErr = pthread_mutex_unlock (&m_oMutex); if (nErr != 0) mjpeg_error_exit1 ("pthread_mutex_unlock() failed: %s", strerror (nErr));}// The ThreadCondition class.// Default constructor.ThreadCondition::ThreadCondition (ThreadMutex &a_rMutex) : m_rMutex (a_rMutex){ int nErr; // An error that may occur. pthread_condattr_t sCondAttr; // Attributes for the condition. // Initialize the condition. nErr = pthread_condattr_init (&sCondAttr); if (nErr != 0) mjpeg_error_exit1 ("pthread_condattr_init() failed: %s", strerror (nErr)); nErr = pthread_cond_init (&m_oCondition, &sCondAttr); if (nErr != 0) mjpeg_error_exit1 ("pthread_cond_init() failed: %s", strerror (nErr)); nErr = pthread_condattr_destroy (&sCondAttr); if (nErr != 0) mjpeg_error_exit1 ("pthread_condattr_destroy() failed: %s", strerror (nErr)); // Initialize the flag. m_bFlag = false;}// Destructor.ThreadCondition::~ThreadCondition(){ int nErr; // An error that may occur. // Make sure any signaled condition got taken care of. //assert (!m_bFlag); // Destroy the condition. nErr = pthread_cond_destroy (&m_oCondition); if (nErr != 0) mjpeg_error_exit1 ("pthread_cond_destroy() failed: %s", strerror (nErr));}// Signal the condition.voidThreadCondition::Signal (void){ int nErr; // An error that may occur. // Make sure our mutex is locked. assert (m_rMutex.m_bLocked); // Signal the condition. nErr = pthread_cond_signal (&m_oCondition); if (nErr != 0) mjpeg_error_exit1 ("pthread_cond_signal() failed: %s", strerror (nErr)); // Set the flag. (It may have been set already, but that's OK.) m_bFlag = true;}// Wait for the condition to be signaled.voidThreadCondition::Wait (void){ int nErr; // An error that may occur. // Make sure our mutex is locked. assert (m_rMutex.m_bLocked); // If a condition hasn't been signaled yet, wait for one to be. if (!m_bFlag) { // Wait for the condition to be signaled. nErr = pthread_cond_wait (&m_oCondition, m_rMutex); if (nErr != 0) mjpeg_error_exit1 ("pthread_cond_wait() failed: %s", strerror (nErr)); // Make sure the condition was signaled properly. assert (m_bFlag);#ifndef NDEBUG // The mutex is still locked, though it may not know it. m_rMutex.m_bLocked = true;#endif // NDEBUG } // Clear the flag. m_bFlag = false;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -