1 /*****************************************************************************
3 *****************************************************************************
4 * Copyright (C) 2003 the VideoLAN team
7 * Authors: Cyril Deguet <asmax@via.ecp.fr>
8 * Olivier Teulière <ipkiss@via.ecp.fr>
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
23 *****************************************************************************/
25 #include "async_queue.hpp"
26 #include "../src/os_factory.hpp"
27 #include "../src/os_timer.hpp"
30 AsyncQueue::AsyncQueue( intf_thread_t *pIntf ): SkinObject( pIntf ),
33 // Initialize the mutex
34 vlc_mutex_init( &m_lock );
37 OSFactory *pOsFactory = OSFactory::instance( pIntf );
38 m_pTimer = pOsFactory->createOSTimer( m_cmdFlush );
40 // Flush the queue every 10 ms
41 m_pTimer->start( 10, false );
45 AsyncQueue::~AsyncQueue()
48 vlc_mutex_destroy( &m_lock );
52 AsyncQueue *AsyncQueue::instance( intf_thread_t *pIntf )
54 if( ! pIntf->p_sys->p_queue )
57 pQueue = new AsyncQueue( pIntf );
60 // Initialization succeeded
61 pIntf->p_sys->p_queue = pQueue;
64 return pIntf->p_sys->p_queue;
68 void AsyncQueue::destroy( intf_thread_t *pIntf )
70 if( pIntf->p_sys->p_queue )
72 delete pIntf->p_sys->p_queue;
73 pIntf->p_sys->p_queue = NULL;
78 void AsyncQueue::push( const CmdGenericPtr &rcCommand, bool removePrev )
82 // Remove the commands of the same type
83 remove( rcCommand.get()->getType(), rcCommand );
85 m_cmdList.push_back( rcCommand );
89 void AsyncQueue::remove( const string &rType, const CmdGenericPtr &rcCommand )
91 vlc_mutex_lock( &m_lock );
93 list<CmdGenericPtr>::iterator it;
94 for( it = m_cmdList.begin(); it != m_cmdList.end(); it++ )
96 // Remove the command if it is of the given type
97 if( (*it).get()->getType() == rType )
99 // Maybe the command wants to check if it must really be
101 if( rcCommand.get()->checkRemove( (*it).get() ) == true )
103 list<CmdGenericPtr>::iterator itNew = it;
105 m_cmdList.erase( it );
111 vlc_mutex_unlock( &m_lock );
115 void AsyncQueue::flush()
119 vlc_mutex_lock( &m_lock );
121 if( m_cmdList.size() > 0 )
123 // Pop the first command from the queue
124 CmdGenericPtr cCommand = m_cmdList.front();
125 m_cmdList.pop_front();
127 // Unlock the mutex to avoid deadlocks if another thread wants to
128 // enqueue/remove a command while this one is processed
129 vlc_mutex_unlock( &m_lock );
131 // Execute the command
132 cCommand.get()->execute();
136 vlc_mutex_unlock( &m_lock );
143 void AsyncQueue::CmdFlush::execute()