解決libvlc_media_player_stop時死鎖的方法


轉自:http://www.jiazi.cn/blog/?id=56 擴散該解決方法

 

最近需要使用VLC控件來做一個簡單的流媒體播放器,在實施過程中,發現在調用libvlc_media_player_stop()方法時有時會卡死。

百度告訴我可能是死鎖問題,即在libvlc的回調事件中可能阻塞了,解決方法是另外開個線程來調用libvlc_media_player_stop()方法。

可是,我並沒有用到回調事件。雖然另外開個線程來調用libvlc_media_player_stop()能解決問題,但多線程可能會帶來更多的隱患。

 

通過幾番測試后,我發現如果不將vlc視頻嵌入到子窗口中播放,而是讓它獨立窗口播放,則在libvlc_media_player_stop()時是不會卡死的。

於是判斷可能是VLC在stop的過程中可能會產生子窗口消息,然而子窗口消息是在主線程(UI線程)中處理的,而libvlc_media_player_stop()方法也是在主線程中調用的,這就造成了競爭性死鎖。

如果視頻不是嵌入到子窗口中,而是獨立存在(VLC內部自己創建的),則其消息處理非主線程負責,就不會出現競爭性死鎖。

 

原因找出,解決方案如下:

1、另外開個線調來調用libvlc_media_player_stop()方法。(這是我在百度上找到的方法,但我認為該方法不夠完美)

2、在libvlc_media_player_stop()之前,先把“包含VLC視頻窗口”的子窗口銷毀,后面如果需要再重建。由於窗口不存在了,VLC在stop的過程中的任何消息都不會發到主線程中來了,這樣就不會出現競爭性死鎖了。(反復測試后再也沒有出現死鎖的問題了)

 

方法二code:

const QString play_url("rtmp://live.hkstv.hk.lxdns.com/live/hks");
libvlc_instance_t *m_inst = NULL;
libvlc_media_player_t *m_mp = NULL;
libvlc_media_t *m_m = NULL;
QWidget *m_videoWdg = NULL;

const char * const vlc_args[] = {
  "--no-audio",
  "--demux=h264",
  "--rtsp-frame-buffer-size=1000000", //RTSP幀緩沖大小,默認大小為100000
  "--network-caching=300",
  "--rtsp-tcp"
};


m_inst = libvlc_new(sizeof(vlc_args) / sizeof(vlc_args[0]), vlc_args);

m_m = libvlc_media_new_location(m_inst, play_url.toStdString().c_str());

m_mp = libvlc_media_player_new_from_media(m_m);

libvlc_media_parse(m_m);

libvlc_media_release(m_m);

m_videoWdg = new QWidget;

HWND screen_hwnd = (HWND)m_videoWdg->winId();

libvlc_media_player_set_hwnd(m_mp, screen_hwnd);

if (libvlc_media_player_play(m_mp) == -1)
{
  //libvlc_media_player_play error
  return;
}

 

//停止播放時,先釋放掉綁定vlc的播放窗口,然后調用vlc庫函數,停止播放。

void  stopPlay()
{
  
  if (m_mp)
  {

    //釋放掉綁定vlc的播放窗口
    if (m_videoWdg != nullptr)
    {
      delete m_videoWdg;
      m_videoWdg = nullptr;
    }

    //停掉流媒體
    libvlc_media_player_stop(m_mp);
    libvlc_media_player_release(m_mp);
    libvlc_release(m_inst);

    m_inst = NULL;
    m_mp = NULL;
    m_m = NULL;
  }
}

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM