如果发生如题现象,请想一下自己的程序的如上操作与RTSPServer的taskScheduler是否是用一个线程。
详细说明如下:
live555是一个单线程event驱动模式。因为是一个开源库,大家在使用时,往往给与一个线程来驱动rtsp taskScheduler的doEventLoop。
在之外有其他的线程来完成业务的处理(例如:接收向rtsp ServerMediaSession放入的数据)。
因为要使用ServerMediaSession来对应相应的rtsp地址提供服务,需要向RTSPServer中的添加或者删除ServerMediaSession。这两个动作往往使用的不是驱动rtsp taskScheduler的线程。
而Class RTSPServer:: public GenericMediaServer中对保存ServerMediaSession的列表的增删操作,并没有多线程的保护机制。
所以,大家可以向taskScheduler提交task,使用taskScheduler的线程来增删RTSPServer中的ServerMediaSession成员,避免多线程同时操纵同一资源导致系统崩溃问题的发生。
void GenericMediaServer::addServerMediaSession(ServerMediaSession* serverMediaSession) {
if (serverMediaSession == NULL) return;
char const* sessionName = serverMediaSession->streamName();
if (sessionName == NULL) sessionName = "";
removeServerMediaSession(sessionName); // in case an existing "ServerMediaSession" with this name already exists
fServerMediaSessions->Add(sessionName, (void*)serverMediaSession);
}
void GenericMediaServer::removeServerMediaSession(ServerMediaSession* serverMediaSession) {
if (serverMediaSession == NULL) return;
fServerMediaSessions->Remove(serverMediaSession->streamName());
if (serverMediaSession->referenceCount() == 0) {
Medium::close(serverMediaSession);
} else {
serverMediaSession->deleteWhenUnreferenced() = True;
}
}