@@ -1831,28 +1831,6 @@ c2_status_t MfxC2DecoderComponent::AllocateC2Block(uint32_t width, uint32_t heig
18311831 C2MemoryUsage mem_usage = {m_consumerUsage, C2AndroidMemoryUsage::HW_CODEC_WRITE};
18321832 res = m_c2Allocator->fetchGraphicBlock (width, height,
18331833 MfxFourCCToGralloc (fourcc), mem_usage, out_block);
1834- if (res == C2_OK) {
1835- auto hndl_deleter = [](native_handle_t *hndl) {
1836- native_handle_delete (hndl);
1837- hndl = nullptr ;
1838- };
1839-
1840- std::unique_ptr<native_handle_t , decltype (hndl_deleter)> hndl (
1841- android::UnwrapNativeCodec2GrallocHandle ((*out_block)->handle ()), hndl_deleter);
1842-
1843- uint64_t id;
1844- if (C2_OK != MfxGrallocInstance::getInstance ()->GetBackingStore (hndl.get (), &id))
1845- return C2_CORRUPTED;
1846- if (!m_vppConversion) {
1847- if (m_allocator && !m_allocator->InCache (id)) {
1848- res = C2_BLOCKING;
1849- std::this_thread::sleep_for (std::chrono::milliseconds (1 ));
1850- // If always fetch a nocached block, check if width or height have changed
1851- // compare to when it was initialized.
1852- MFX_DEBUG_TRACE_STREAM (" fetchGraphicBlock a nocached block, please retune output blocks. id = " << id);
1853- }
1854- }
1855- }
18561834 } else if (m_mfxVideoParams.IOPattern == MFX_IOPATTERN_OUT_SYSTEM_MEMORY) {
18571835 C2MemoryUsage mem_usage = {m_consumerUsage, C2MemoryUsage::CPU_WRITE};
18581836 res = m_c2Allocator->fetchGraphicBlock (width, height,
@@ -1934,12 +1912,57 @@ c2_status_t MfxC2DecoderComponent::AllocateFrame(MfxC2FrameOut* frame_out, bool
19341912 }
19351913 m_surfaces.emplace (id, frame_out->GetMfxFrameSurface ());
19361914 } else {
1937- if (it->second ->Data .Locked ) {
1938- /* Buffer locked, try next block. */
1939- MFX_DEBUG_TRACE_PRINTF (" Buffer still locked, try next block" );
1940- res = C2_TIMED_OUT;
1941- } else {
1915+ if (!it->second ->Data .Locked ) {
19421916 *frame_out = MfxC2FrameOut (std::move (out_block), it->second );
1917+ } else {
1918+ // when surface detached in framework, keep AllocateC2Block until we get an unlocked surface.
1919+ std::list<C2GraphicBlock> block_pool;
1920+ std::shared_ptr<C2GraphicBlock> new_block;
1921+ bool found_surface = false ;
1922+
1923+ while (it != m_surfaces.end () && !found_surface) {
1924+ // Buffer locked, try next block.
1925+ res = AllocateC2Block (MFXGetSurfaceWidth (m_mfxVideoParams.mfx .FrameInfo , m_mfxVideoParams.IOPattern == MFX_IOPATTERN_OUT_VIDEO_MEMORY),
1926+ MFXGetSurfaceHeight (m_mfxVideoParams.mfx .FrameInfo , m_mfxVideoParams.IOPattern == MFX_IOPATTERN_OUT_VIDEO_MEMORY),
1927+ m_mfxVideoParams.mfx .FrameInfo .FourCC , &new_block);
1928+
1929+ if (C2_TIMED_OUT == res) continue ;
1930+
1931+ if (C2_OK != res) break ;
1932+
1933+ block_pool.push_back (*new_block);
1934+
1935+ std::unique_ptr<native_handle_t , decltype (hndl_deleter)> new_hndl (
1936+ android::UnwrapNativeCodec2GrallocHandle (new_block->handle ()), hndl_deleter);
1937+
1938+ if (new_hndl == nullptr )
1939+ {
1940+ return C2_NO_MEMORY;
1941+ }
1942+
1943+ it = m_surfaces.end ();
1944+
1945+ if (C2_OK != MfxGrallocInstance::getInstance ()->GetBackingStore (new_hndl.get (), &id))
1946+ {
1947+ return C2_CORRUPTED;
1948+ }
1949+
1950+ it = m_surfaces.find (id);
1951+
1952+ if (C2_OK == res && (it == m_surfaces.end () || (it != m_surfaces.end () && !it->second ->Data .Locked ))) {
1953+ block_pool.clear ();
1954+ found_surface = true ;
1955+ if (it == m_surfaces.end ()) {
1956+ res = MfxC2FrameOut::Create (converter, std::move (new_block), m_mfxVideoParams.mfx .FrameInfo , frame_out, new_hndl.get ());
1957+ if (C2_OK != res) {
1958+ break ;
1959+ }
1960+ m_surfaces.emplace (id, frame_out->GetMfxFrameSurface ());
1961+ } else {
1962+ *frame_out = MfxC2FrameOut (std::move (new_block), it->second );
1963+ }
1964+ }
1965+ }
19431966 }
19441967 }
19451968 } else {
0 commit comments