示例#1
0
void QTSServerInterface::SetValueComplete(UInt32 inAttrIndex, QTSSDictionaryMap* inMap,
							UInt32 inValueIndex, void* inNewValue, UInt32 inNewValueLen)
{
    if (inAttrIndex == qtssSvrState)
    {
        Assert(inNewValueLen == sizeof(QTSS_ServerState));
        
        //
        // Invoke the server state change role
        QTSS_RoleParams theParams;
        theParams.stateChangeParams.inNewState = *(QTSS_ServerState*)inNewValue;
        
        static QTSS_ModuleState sStateChangeState = { NULL, 0, NULL, false };
        if (OSThread::GetCurrent() == NULL)
            OSThread::SetMainThreadData(&sStateChangeState);
        else
            OSThread::GetCurrent()->SetThreadData(&sStateChangeState);

        UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kStateChangeRole);
        {
            for (UInt32 theCurrentModule = 0; theCurrentModule < numModules; theCurrentModule++)
            {  
                QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kStateChangeRole, theCurrentModule);
                (void)theModule->CallDispatch(QTSS_StateChange_Role, &theParams);
            }
        }

        //
        // Make sure to clear out the thread data
        if (OSThread::GetCurrent() == NULL)
            OSThread::SetMainThreadData(NULL);
        else
            OSThread::GetCurrent()->SetThreadData(NULL);
    }
}
示例#2
0
void QTSServer::DoInitRole()
{
    QTSS_RoleParams theInitParams;
    theInitParams.initParams.inServer =         this;
    theInitParams.initParams.inPrefs =          fSrvrPrefs;
    theInitParams.initParams.inMessages =       fSrvrMessages;
    theInitParams.initParams.inErrorLogStream = &sErrorLogStream;
        
    QTSS_ModuleState theModuleState;
    theModuleState.curRole = QTSS_Initialize_Role;
    theModuleState.curTask = NULL;
    OSThread::SetMainThreadData(&theModuleState);
	
    for (UInt32 x = 0; x < QTSServerInterface::GetNumModulesInRole(QTSSModule::kInitializeRole); x++)
    {
        QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kInitializeRole, x);
        theInitParams.initParams.inModule = theModule;
        theModuleState.curModule = theModule;
        QTSS_Error theErr = theModule->CallDispatch(QTSS_Initialize_Role, &theInitParams);

        if (theErr != QTSS_NoErr)
        {
            // If the module reports an error when initializing itself,
            // delete the module and pretend it was never there.
            QTSSModuleUtils::LogError(qtssWarningVerbosity, qtssMsgInitFailed, theErr,
                                            theModule->GetValue(qtssModName)->Ptr);
                                            
            sModuleQueue.Remove(theModule->GetQueueElem());
            delete theModule;
        }
    }

    OSThread::SetMainThreadData(NULL);
}
示例#3
0
SInt64 ReflectorSessionCheckTask::Run()
{
	OSRefTable* reflectorSessionMap = QTSServerInterface::GetServer()->GetReflectorSessionMap();

	OSMutexLocker locker(reflectorSessionMap->GetMutex());

	SInt64 sNowTime = OS::Milliseconds();
	for (OSRefHashTableIter theIter(reflectorSessionMap->GetHashTable()); !theIter.IsDone(); theIter.Next())
	{
		OSRef* theRef = theIter.GetCurrent();
		ReflectorSession* theSession = (ReflectorSession*)theRef->GetObject();

		SInt64  sCreateTime = theSession->GetInitTimeMS();
		if( (theSession->GetNumOutputs() == 0) && (sNowTime-sCreateTime >= 20*1000) )
		{
			QTSS_RoleParams theParams;
			theParams.easyFreeStreamParams.inStreamName = theSession->GetStreamName();
			UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kEasyCMSFreeStreamRole);
			for ( UInt32 currentModule=0;currentModule < numModules; currentModule++)
			{			
				qtss_printf("没有客户端观看当前转发媒体\n");
				QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kEasyCMSFreeStreamRole, currentModule);
				(void)theModule->CallDispatch(Easy_CMSFreeStream_Role, &theParams);
			}
		}
	}  
	return 30*1000;//30s
}
示例#4
0
void ReflectorSession::DelRedisLive()
{
	QTSS_RoleParams theParams;
	theParams.easyStreamInfoParams.inStreamName = fSessionName.Ptr;
	theParams.easyStreamInfoParams.inChannel = fChannelNum;
	theParams.easyStreamInfoParams.inAction = easyRedisActionDelete;
	UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kRedisUpdateStreamInfoRole);
	for (UInt32 currentModule = 0; currentModule < numModules; currentModule++)
	{
		qtss_printf("从redis中删除推流名称%s\n", fSourceID.Ptr);
		QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kRedisUpdateStreamInfoRole, currentModule);
		(void)theModule->CallDispatch(Easy_RedisUpdateStreamInfo_Role, &theParams);
	}
}
示例#5
0
Bool16 QTSServer::Initialize(XMLPrefsParser* inPrefsSource, PrefsSource* inMessagesSource, UInt16 inPortOverride, Bool16 createListeners)
{
    fServerState = qtssFatalErrorState;
    sPrefsSource = inPrefsSource;
    sMessagesSource = inMessagesSource;
    this->InitCallbacks();

	fMediaSource = NULL;
    //
    // DICTIONARY INITIALIZATION
    
    QTSSModule::Initialize();
    QTSServerPrefs::Initialize();
    QTSSMessages::Initialize();
    QTSSFile::Initialize();
    
    //
    // STUB SERVER INITIALIZATION
    //
    // Construct stub versions of the prefs and messages dictionaries. We need
    // both of these to initialize the server, but they have to be stubs because
    // their QTSSDictionaryMaps will presumably be modified when modules get loaded.
    
    fSrvrPrefs = new QTSServerPrefs(inPrefsSource, false); // First time, don't write changes to the prefs file
    fSrvrMessages = new QTSSMessages(inMessagesSource);
    QTSSModuleUtils::Initialize(fSrvrMessages, this, QTSServerInterface::GetErrorLogStream());

	SetAssertLogger(this->GetErrorLogStream());// the error log stream is our assert logger
        
    // Load ERROR LOG module only. This is good in case there is a startup error.
    
    QTSSModule* theLoggingModule = new QTSSModule("QTSSErrorLogModule");
    (void)theLoggingModule->SetupModule(&sCallbacks, &QTSSErrorLogModule_Main);
    (void)AddModule(theLoggingModule);
    this->BuildModuleRoleArrays();

    //
    // STARTUP TIME - record it
    fStartupTime_UnixMilli = OS::Milliseconds();
    fGMTOffset = OS::GetGMTOffset();
    
    if ( fNumListeners == 0 )
    {  
		if (createListeners)
            QTSSModuleUtils::LogError(qtssWarningVerbosity, qtssMsgNoPortsSucceeded, 0);
    }

    fServerState = qtssStartingUpState;
    return true;
}
示例#6
0
void EasyCMSSession::stopPushStream()
{
	QTSS_RoleParams params;

	QTSS_Error errCode = QTSS_NoErr;
	UInt32 fCurrentModule = 0;
	UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kStopStreamRole);
	for (; fCurrentModule < numModules; ++fCurrentModule)
	{
		QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kStopStreamRole, fCurrentModule);
		errCode = theModule->CallDispatch(Easy_StopStream_Role, &params);
	}
	fCurrentModule = 0;
}
示例#7
0
SInt64 EasyCameraSource::Run()
{
	QTSS_Error theErr = QTSS_NoErr;
	EventFlags events = this->GetEvents();

	if(events & Task::kTimeoutEvent)
	{
		//向设备获取快照数据
		//unsigned char *sData = (unsigned char*)malloc(EASY_SNAP_BUFFER_SIZE);
		unsigned char *sData = new unsigned char[EASY_SNAP_BUFFER_SIZE];
		int snapBufLen = 0;

		do{
			//如果获取到摄像机快照数据,Base64编码/发送
			if (!getSnapData(sData, EASY_SNAP_BUFFER_SIZE, &snapBufLen))
			{
				//未获取到数据
				qtss_printf("EasyCameraSource::Run::GetSnapData() => Get Snap Data Fail \n");
				theErr = QTSS_ValueNotFound;
				break;
			}

			QTSS_RoleParams params;
			params.postSnapParams.snapLen = snapBufLen;
			params.postSnapParams.snapPtr = sData;
			params.postSnapParams.snapType = EASY_SNAP_TYPE_JPEG;
			UInt32 fCurrentModule = 0;
			UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kPostSnapRole);
			for (; fCurrentModule < numModules; fCurrentModule++)
			{
				qtss_printf("EasyCameraSource::Run::kPostSnapRole\n");
				QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kPostSnapRole, fCurrentModule);
				(void)theModule->CallDispatch(Easy_PostSnap_Role, &params);	
				break;
			}
			break;

		}while(0);

		//free((void*)sData);
		delete []sData;
		sData = NULL;

		fTimeoutTask->RefreshTimeout();
	}

	return 0;
}
示例#8
0
QTSS_Error QTSSCallbacks::Easy_StopHLSession(const char* inSessionName)
{
	QTSS_RoleParams packetParams;
	packetParams.easyHLSCloseParams.inStreamName = (char*)inSessionName;

	UInt32 fCurrentModule = 0;
	UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kEasyHLSCloseRole);
	for (; fCurrentModule < numModules; fCurrentModule++)
	{
		QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kEasyHLSCloseRole, fCurrentModule);
		(void)theModule->CallDispatch(Easy_HLSClose_Role, &packetParams);
		return QTSS_NoErr;
	}
	
	return QTSS_RequestFailed;
}
示例#9
0
void QTSServer::DoInitRole()
{
    QTSS_RoleParams theInitParams;
    theInitParams.initParams.inServer =         this;
    theInitParams.initParams.inPrefs =          fSrvrPrefs;
    theInitParams.initParams.inMessages =       fSrvrMessages;
    theInitParams.initParams.inErrorLogStream = &sErrorLogStream;
        
    QTSS_ModuleState theModuleState;
    theModuleState.curRole = QTSS_Initialize_Role;
    theModuleState.curTask = NULL;
    OSThread::SetMainThreadData(&theModuleState);

    //
    // Add the OPTIONS method as the one method the server handles by default (it handles
    // it internally). Modules that handle other RTSP methods will add 
    QTSS_RTSPMethod theOptionsMethod = qtssOptionsMethod;
    (void)this->SetValue(qtssSvrHandledMethods, 0, &theOptionsMethod, sizeof(theOptionsMethod));


// For now just disable the SetParameter to be compatible with Real.  It should really be removed only for clients that have problems with their SetParameter implementations like (Real Players).
// At the moment it isn't necesary to add the option.
//   QTSS_RTSPMethod	theSetParameterMethod = qtssSetParameterMethod;
//    (void)this->SetValue(qtssSvrHandledMethods, 0, &theSetParameterMethod, sizeof(theSetParameterMethod));
	
    for (UInt32 x = 0; x < QTSServerInterface::GetNumModulesInRole(QTSSModule::kInitializeRole); x++)
    {
        QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kInitializeRole, x);
        theInitParams.initParams.inModule = theModule;
        theModuleState.curModule = theModule;
        QTSS_Error theErr = theModule->CallDispatch(QTSS_Initialize_Role, &theInitParams);

        if (theErr != QTSS_NoErr)
        {
            // If the module reports an error when initializing itself,
            // delete the module and pretend it was never there.
            QTSSModuleUtils::LogError(qtssWarningVerbosity, qtssMsgInitFailed, theErr,
                                            theModule->GetValue(qtssModName)->Ptr);
                                            
            sModuleQueue.Remove(theModule->GetQueueElem());
            delete theModule;
        }
    }

    OSThread::SetMainThreadData(NULL);
}
示例#10
0
QTSS_Error QTSSCallbacks::Easy_ListRecordFiles(const char* inSessionName, const char* inBeginTime, const char* inEndTime, vector<string> *outRecordFiles)
{
	QTSS_RoleParams packetParams;
	packetParams.easyRecordListParams.inStreamName = (char*)inSessionName;
	packetParams.easyRecordListParams.inBeginTime = (char*)inBeginTime;
	packetParams.easyRecordListParams.inEndTime = (char*)inEndTime;
	packetParams.easyRecordListParams.outRecords = outRecordFiles;

	UInt32 fCurrentModule = 0;
	UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kRecordListRole);
	for (; fCurrentModule < numModules; fCurrentModule++)
	{
		QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kRecordListRole, fCurrentModule);
		(void)theModule->CallDispatch(Easy_RecordList_Role, &packetParams);
		return QTSS_NoErr;
	}
	return QTSS_RequestFailed;
}
示例#11
0
QTSS_Error ReflectorSession::SetSessionName()
{
	if (fSourceID.Len > 0)
	{
		QTSS_RoleParams theParams;
		theParams.easyStreamInfoParams.inStreamName = fSessionName.Ptr;
		theParams.easyStreamInfoParams.inChannel = fChannelNum;
		theParams.easyStreamInfoParams.inNumOutputs = fNumOutputs;
		theParams.easyStreamInfoParams.inAction = easyRedisActionSet;
		auto numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kRedisUpdateStreamInfoRole);
		for (UInt32 currentModule = 0; currentModule < numModules; currentModule++)
		{
			QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kRedisUpdateStreamInfoRole, currentModule);
			(void)theModule->CallDispatch(Easy_RedisUpdateStreamInfo_Role, &theParams);
		}
	}
	return QTSS_NoErr;
}
示例#12
0
QTSS_Error QTSSCallbacks::Easy_StartHLSession(const char* inSessionName, const char* inURL, UInt32 inTimeout, char* outURL)
{
	QTSS_RoleParams params;
	params.easyHLSOpenParams.inStreamName = (char*)inSessionName;
	params.easyHLSOpenParams.inRTSPUrl = (char*)inURL;
	params.easyHLSOpenParams.inTimeout = inTimeout;
	params.easyHLSOpenParams.outHLSUrl = outURL;

	UInt32 fCurrentModule = 0;
	UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kEasyHLSOpenRole);
	for (; fCurrentModule < numModules; fCurrentModule++)
	{
		QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kEasyHLSOpenRole, fCurrentModule);
		(void)theModule->CallDispatch(Easy_HLSOpen_Role, &params);	
		return QTSS_NoErr;
	}
	
	return QTSS_RequestFailed;
}
示例#13
0
QTSS_Error  QTSSCallbacks::QTSS_SetIdleRoleTimer(SInt64 inMsecToWait)
{

    QTSS_ModuleState* theState = (QTSS_ModuleState*)OSThread::GetMainThreadData();
    if (OSThread::GetCurrent() != NULL)
        theState = (QTSS_ModuleState*)OSThread::GetCurrent()->GetThreadData();
    
    // This may happen if this callback is occurring on module-created thread
    if (theState == NULL)
        return QTSS_RequestFailed;
        
    if (theState->curModule == NULL)
        return QTSS_RequestFailed;


    QTSSModule* theModule = theState->curModule;
    QTSS_ModuleState* thePrivateModuleState = theModule->GetModuleState();
    thePrivateModuleState->idleTime = inMsecToWait;
    theModule->Signal(Task::kUpdateEvent); 
	
    return QTSS_NoErr;
}
void HTTPSessionInterface::UnRegDevSession()
{
	if (fAuthenticated)
	{
		char msgStr[512];
		qtss_snprintf(msgStr, sizeof(msgStr), "Device unregister,Device_serial[%s]\n", fDevice.serial_.c_str());
		QTSServerInterface::LogError(qtssMessageVerbosity, msgStr);

		QTSServerInterface::GetServer()->GetDeviceSessionMap()->UnRegister(fDevice.serial_);//add
		//在redis上删除设备
		//QTSServerInterface::GetServer()->RedisDelDevName(fDevice.serial_.c_str());

		QTSS_RoleParams theParams;
		theParams.StreamNameParams.inStreamName = (char *)(fDevice.serial_.c_str());
		UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kDelDevNameRole);
		for ( UInt32 currentModule=0;currentModule < numModules; currentModule++)
		{
			QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kDelDevNameRole, currentModule);
			(void)theModule->CallDispatch(QTSS_DelDevName_Role, &theParams);
		}
	}
}
示例#15
0
void QTSServer::BuildModuleRoleArrays()
{
    OSQueueIter theIter(&sModuleQueue);
    QTSSModule* theModule = NULL;
        
    // Make sure these variables are cleaned out in case they've already been inited.
    
    DestroyModuleRoleArrays();

    // Loop through all the roles of all the modules, recording the number of
    // modules in each role, and also recording which modules are doing what.
    
    for (UInt32 x = 0; x < QTSSModule::kNumRoles; x++)
    {
        sNumModulesInRole[x] = 0;
        for (theIter.Reset(); !theIter.IsDone(); theIter.Next())
        {
            theModule = (QTSSModule*)theIter.GetCurrent()->GetEnclosingObject();
            if (theModule->RunsInRole(x))
                sNumModulesInRole[x] += 1;
        }
    
        if (sNumModulesInRole[x] > 0)
        {
            UInt32 moduleIndex = 0;
            sModuleArray[x] = new QTSSModule*[sNumModulesInRole[x] + 1];
            for (theIter.Reset(); !theIter.IsDone(); theIter.Next())
            {
                theModule = (QTSSModule*)theIter.GetCurrent()->GetEnclosingObject();
                if (theModule->RunsInRole(x))
                {
                    sModuleArray[x][moduleIndex] = theModule;
                    moduleIndex++;
                }
            }
        }
    }
}
示例#16
0
void    QTSServer::LoadCompiledInModules()
{
#ifndef DSS_DYNAMIC_MODULES_ONLY
    // MODULE DEVELOPERS SHOULD ADD THE FOLLOWING THREE LINES OF CODE TO THIS
    // FUNCTION IF THEIR MODULE IS BEING COMPILED INTO THE SERVER.
    //
    // QTSSModule* myModule = new QTSSModule("__MODULE_NAME__");
    // (void)myModule->Initialize(&sCallbacks, &__MODULE_MAIN_ROUTINE__);
    // (void)AddModule(myModule);
    //
    // The following modules are all compiled into the server. 

#endif //DSS_DYNAMIC_MODULES_ONLY

	QTSSModule* theCMSModule = new QTSSModule("EasyCMSModule");
    (void)theCMSModule->SetupModule(&sCallbacks, &EasyCMSModule_Main);
    (void)AddModule(theCMSModule);

	QTSSModule* theCameraModule = new QTSSModule("EasyCameraModule");
    (void)theCameraModule->SetupModule(&sCallbacks, &EasyCameraModule_Main);
    (void)AddModule(theCameraModule);

}
void HTTPSessionInterface::UnRegDevSession() const
{
    if (fAuthenticated)
    {
        char msgStr[512];
        qtss_snprintf(msgStr, sizeof(msgStr), "Device unregister£¬Device_serial[%s]\n", device_->serial_.c_str());
        QTSServerInterface::LogError(qtssMessageVerbosity, msgStr);

        QTSServerInterface::GetServer()->GetDeviceSessionMap()->UnRegister(device_->serial_);//add
        //ÔÚredisÉÏɾ³ýÉ豸
        //QTSServerInterface::GetServer()->RedisDelDevice(fDevice.serial_.c_str());

        QTSS_RoleParams theParams;
		theParams.DeviceInfoParams.serial_ = new char[64];
		strncpy(theParams.DeviceInfoParams.serial_, device_->serial_.c_str(), device_->serial_.size() + 1);
        UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kRedisDelDeviceRole);
        for (UInt32 currentModule = 0; currentModule < numModules; currentModule++)
        {
            QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kRedisDelDeviceRole, currentModule);
            (void)theModule->CallDispatch(Easy_RedisDelDevice_Role, &theParams);
        }
		delete[] theParams.DeviceInfoParams.serial_;
    }
}
示例#18
0
void RunServer()
{   
    Bool16 restartServer = false;
    UInt32 loopCount = 0;
    UInt32 debugLevel = 0;
    Bool16 printHeader = false;
    Bool16 printStatus = false;
	UInt32 num=0;

    //just wait until someone stops the server or a fatal error occurs.
    QTSS_ServerState theServerState = sServer->GetServerState();
    while ((theServerState != qtssShuttingDownState) &&
            (theServerState != qtssFatalErrorState))
    {
#ifdef __sgi__
        OSThread::Sleep(999);
#else
        OSThread::Sleep(1000);
#endif

		//add,redis,¶¨Ê±±£»î
		num++;
		if(num%5==0)
		{
			num=0;

			UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kRedisTTLRole);
			for ( UInt32 currentModule=0;currentModule < numModules; currentModule++)
			{
				QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kRedisTTLRole, currentModule);
				(void)theModule->CallDispatch(Easy_RedisTTL_Role, NULL);
			}
		}
		//

        LogStatus(theServerState);

        if (sStatusUpdateInterval)
        {
            debugLevel = sServer->GetDebugLevel();             
            printHeader = PrintHeader(loopCount);
            printStatus = PrintLine(loopCount);
                
            if (printStatus)
            {
                if  (DebugOn(sServer) ) // debug level display or logging is on
                    DebugStatus(debugLevel, printHeader);
                
                if (!DebugDisplayOn(sServer))
                    PrintStatus(printHeader); // default status output
            }
            
            
            loopCount++;

        }
        
        if ((sServer->SigIntSet()) || (sServer->SigTermSet()))
        {
            //
            // start the shutdown process
            theServerState = qtssShuttingDownState;
            (void)QTSS_SetValue(QTSServerInterface::GetServer(), qtssSvrState, 0, &theServerState, sizeof(theServerState));

            if (sServer->SigIntSet())
                restartServer = true;
        }
        
        theServerState = sServer->GetServerState();
        if (theServerState == qtssIdleState)
            sServer->KillAllRTPSessions();
    }
    
    //
    // Kill all the sessions and wait for them to die,
    // but don't wait more than 5 seconds
    sServer->KillAllRTPSessions();
    for (UInt32 shutdownWaitCount = 0; (sServer->GetNumRTPSessions() > 0) && (shutdownWaitCount < 5); shutdownWaitCount++)
        OSThread::Sleep(1000);
        
    //Now, make sure that the server can't do any work
    TaskThreadPool::RemoveThreads();
    
    //now that the server is definitely stopped, it is safe to initate
    //the shutdown process
    delete sServer;
    
    CleanPid(false);
    //ok, we're ready to exit. If we're quitting because of some fatal error
    //while running the server, make sure to let the parent process know by
    //exiting with a nonzero status. Otherwise, exit with a 0 status
    if (theServerState == qtssFatalErrorState || restartServer)
        ::exit (-2);//-2 signals parent process to restart server
}
示例#19
0
QTSS_Error EasyCMSSession::processMessage()
{
	if (NULL == fRequest) return QTSS_BadArgument;

	QTSS_Error theErr = fRequest->Parse();
	if (theErr != QTSS_NoErr)
		return QTSS_BadArgument;

	//获取具体Content json数据部分
	StrPtrLen* lengthPtr = fRequest->GetHeaderValue(httpContentLengthHeader);
	StringParser theContentLenParser(lengthPtr);
	theContentLenParser.ConsumeWhitespace();
	UInt32 content_length = theContentLenParser.ConsumeInteger(NULL);

	if (content_length)
	{
		qtss_printf("EasyCMSSession::ProcessMessage read content-length:%lu \n", content_length);
		// 检查content的fContentBuffer和fContentBufferOffset是否有值存在,如果存在,说明我们已经开始
		// 进行content请求处理,如果不存在,我们需要创建并初始化fContentBuffer和fContentBufferOffset
		if (fContentBuffer == NULL)
		{
			fContentBuffer = NEW char[content_length + 1];
			memset(fContentBuffer, 0, content_length + 1);
			fContentBufferOffset = 0;
		}

		UInt32 theLen = 0;
		// 读取HTTP Content报文数据
		theErr = fInputStream.Read(fContentBuffer + fContentBufferOffset, content_length - fContentBufferOffset, &theLen);
		Assert(theErr != QTSS_BadArgument);

		if (theErr == QTSS_RequestFailed)
		{
			OSCharArrayDeleter charArrayPathDeleter(fContentBuffer);
			fContentBufferOffset = 0;
			fContentBuffer = NULL;

			return QTSS_RequestFailed;
		}

		qtss_printf("EasyCMSSession::ProcessMessage() Add Len:%lu \n", theLen);
		if ((theErr == QTSS_WouldBlock) || (theLen < (content_length - fContentBufferOffset)))
		{
			//
			// Update our offset in the buffer
			fContentBufferOffset += theLen;

			Assert(theErr == QTSS_NoErr);
			return QTSS_WouldBlock;
		}

		Assert(theErr == QTSS_NoErr);

		// 处理完成报文后会自动进行Delete处理
		OSCharArrayDeleter charArrayPathDeleter(fContentBuffer);

		qtss_printf("EasyCMSSession::ProcessMessage() Get Complete Msg:\n%s", fContentBuffer);

		fNoneACKMsgCount = 0;

		EasyProtocol protocol(fContentBuffer);
		int nNetMsg = protocol.GetMessageType();
		switch (nNetMsg)
		{
		case MSG_SD_REGISTER_ACK:
			{
				EasyMsgSDRegisterACK ack(fContentBuffer);

				qtss_printf("session id = %s\n", ack.GetBodyValue(EASY_TAG_SESSION_ID).c_str());
				qtss_printf("device serial = %s\n", ack.GetBodyValue(EASY_TAG_SERIAL).c_str());
			}
			break;
		case MSG_SD_POST_SNAP_ACK:
			{
				;
			}
			break;
		case MSG_SD_PUSH_STREAM_REQ:
			{
				EasyMsgSDPushStreamREQ	startStreamReq(fContentBuffer);

				string serial = startStreamReq.GetBodyValue(EASY_TAG_SERIAL);
				string ip = startStreamReq.GetBodyValue(EASY_TAG_SERVER_IP);
				string port = startStreamReq.GetBodyValue(EASY_TAG_SERVER_PORT);
				string protocol = startStreamReq.GetBodyValue(EASY_TAG_PROTOCOL);
				string channel = startStreamReq.GetBodyValue(EASY_TAG_CHANNEL);
				string streamID = startStreamReq.GetBodyValue(EASY_TAG_STREAM_ID);
				string reserve = startStreamReq.GetBodyValue(EASY_TAG_RESERVE);

				qtss_printf("Serial = %s\n", serial.c_str());
				qtss_printf("Server_IP = %s\n", ip.c_str());
				qtss_printf("Server_Port = %s\n", port.c_str());

				//TODO::这里需要对传入的Serial/StreamID/Channel做一下容错处理
				if (serial.empty() || ip.empty() || port.empty())
				{
					return QTSS_ValueNotFound;
				}

				QTSS_RoleParams params;

				params.startStreaParams.inIP = ip.c_str();
				params.startStreaParams.inPort = atoi(port.c_str());
				params.startStreaParams.inSerial = serial.c_str();
				params.startStreaParams.inProtocol = protocol.c_str();
				params.startStreaParams.inChannel = channel.c_str();
				params.startStreaParams.inStreamID = streamID.c_str();

				QTSS_Error errCode = QTSS_NoErr;
				UInt32 fCurrentModule = 0;
				UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kStartStreamRole);
				for (; fCurrentModule < numModules; ++fCurrentModule)
				{
					QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kStartStreamRole, fCurrentModule);
					errCode = theModule->CallDispatch(Easy_StartStream_Role, &params);
				}
				fCurrentModule = 0;

				EasyJsonValue body;
				body[EASY_TAG_SERIAL] = params.startStreaParams.inSerial;
				body[EASY_TAG_CHANNEL] = params.startStreaParams.inChannel;
				body[EASY_TAG_PROTOCOL] = params.startStreaParams.inProtocol;
				body[EASY_TAG_SERVER_IP] = params.startStreaParams.inIP;
				body[EASY_TAG_SERVER_PORT] = params.startStreaParams.inPort;
				body[EASY_TAG_RESERVE] = reserve;

				EasyMsgDSPushSteamACK rsp(body, startStreamReq.GetMsgCSeq(), getStatusNo(errCode));

				string msg = rsp.GetMsg();
				StrPtrLen jsonContent((char*)msg.data());
				HTTPRequest httpAck(&QTSServerInterface::GetServerHeader(), httpResponseType);

				if (httpAck.CreateResponseHeader())
				{
					if (jsonContent.Len)
						httpAck.AppendContentLengthHeader(jsonContent.Len);

					//Push msg to OutputBuffer
					char respHeader[2048] = { 0 };
					StrPtrLen* ackPtr = httpAck.GetCompleteHTTPHeader();
					strncpy(respHeader, ackPtr->Ptr, ackPtr->Len);

					fOutputStream.Put(respHeader);
					if (jsonContent.Len > 0)
						fOutputStream.Put(jsonContent.Ptr, jsonContent.Len);
				}
			}
			break;
		case MSG_SD_STREAM_STOP_REQ:
			{
				EasyMsgSDStopStreamREQ stopStreamReq(fContentBuffer);

				QTSS_RoleParams params;

				string serial = stopStreamReq.GetBodyValue(EASY_TAG_SERIAL);
				params.stopStreamParams.inSerial = serial.c_str();
				string protocol = stopStreamReq.GetBodyValue(EASY_TAG_PROTOCOL);
				params.stopStreamParams.inProtocol = protocol.c_str();
				string channel = stopStreamReq.GetBodyValue(EASY_TAG_CHANNEL);
				params.stopStreamParams.inChannel = channel.c_str();

				QTSS_Error errCode = QTSS_NoErr;
				UInt32 fCurrentModule = 0;
				UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kStopStreamRole);
				for (; fCurrentModule < numModules; ++fCurrentModule)
				{
					QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kStopStreamRole, fCurrentModule);
					errCode = theModule->CallDispatch(Easy_StopStream_Role, &params);
				}
				fCurrentModule = 0;

				EasyJsonValue body;
				body[EASY_TAG_SERIAL] = params.stopStreamParams.inSerial;
				body[EASY_TAG_CHANNEL] = params.stopStreamParams.inChannel;
				body[EASY_TAG_PROTOCOL] = params.stopStreamParams.inProtocol;


				EasyMsgDSStopStreamACK rsp(body, stopStreamReq.GetMsgCSeq(), getStatusNo(errCode));
				string msg = rsp.GetMsg();

				//回应
				StrPtrLen jsonContent((char*)msg.data());
				HTTPRequest httpAck(&QTSServerInterface::GetServerHeader(), httpResponseType);

				if (httpAck.CreateResponseHeader())
				{
					if (jsonContent.Len)
						httpAck.AppendContentLengthHeader(jsonContent.Len);

					//Push msg to OutputBuffer
					char respHeader[2048] = { 0 };
					StrPtrLen* ackPtr = httpAck.GetCompleteHTTPHeader();
					strncpy(respHeader, ackPtr->Ptr, ackPtr->Len);

					fOutputStream.Put(respHeader);
					if (jsonContent.Len > 0)
						fOutputStream.Put(jsonContent.Ptr, jsonContent.Len);
				}
			}
			break;
		default:
			break;
		}
	}
示例#20
0
QTSS_Error	QTSSCallbacks::QTSS_Authorize(QTSS_RTSPRequestObject inAuthRequestObject, char** outAuthRealm, Bool16* outAuthUserAllowed)
{
    RTSPRequestInterface* request = (RTSPRequestInterface *) inAuthRequestObject;
    if (request == NULL)
        return QTSS_BadArgument;
            
    // Because this is a role being executed from inside a callback, we need to
    // make sure that QTSS_RequestEvent will not work.
    Task* curTask = NULL;
    QTSS_ModuleState* theState = (QTSS_ModuleState*)OSThread::GetMainThreadData();
    if (OSThread::GetCurrent() != NULL)
        theState = (QTSS_ModuleState*)OSThread::GetCurrent()->GetThreadData();
        
    if (theState != NULL)
        curTask = theState->curTask;
        
    QTSS_RoleParams theParams;
    theParams.rtspRequestParams.inRTSPSession = NULL;
    theParams.rtspRequestParams.inRTSPRequest = request;
    theParams.rtspRequestParams.inClientSession = NULL;

    QTSS_Error theErr = QTSS_RequestFailed;
    UInt32 x = 0;
    UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kRTSPAuthRole);
    QTSSModule* theModulePtr = NULL;
    Bool16 		allowedDefault =  QTSServerInterface::GetServer()->GetPrefs()->GetAllowGuestDefault();
    *outAuthUserAllowed = allowedDefault;
    Bool16      allowed = allowedDefault; //server pref?
    Bool16      hasUser = false; 
    Bool16      handled = false;
    
    
    // Call all the modules that are registered for the RTSP Authorize Role 
    
    for ( ; x < numModules; x++)
    {
        request->SetAllowed(true);  
        request->SetHasUser(false);
        request->SetAuthHandled(false);
    
        debug_printf(" QTSSCallbacks::QTSS_Authorize calling module module = %lu numModules=%lu\n", x,numModules);
        theModulePtr = QTSServerInterface::GetModule(QTSSModule::kRTSPAuthRole, x);
        theErr =  QTSS_NoErr;
        if (theModulePtr)
        {       
            if (__QTSSCALLBACKS_DEBUG__)
                theModulePtr->GetValue(qtssModName)->PrintStr("QTSSModule::CallDispatch ENTER module=", "\n");
           
            theErr = theModulePtr->CallDispatch(QTSS_RTSPAuthorize_Role, &theParams);
            debug_printf(" QTSSCallbacks::QTSS_Authorize calling module module = %lu numModules=%lu ModuleError=%ld\n", x,numModules, theErr);
        }
        else
        {    debug_printf(" QTSSCallbacks::QTSS_Authorize calling module module = %lu is NULL! numModules=%lu\n", x,numModules);
             continue;
        }

        allowed = request->GetAllowed();
        hasUser = request->GetHasUser();
        handled = request->GetAuthHandled();
        debug_printf("QTSSCallbacks::QTSS_Authorize allowedDefault =%d allowed= %d hasUser = %d handled=%d \n",allowedDefault, allowed,hasUser, handled);
    
        *outAuthUserAllowed = allowed;    
        //notes:
        //if (allowed && !handled)  break; //old module               
        //if (!allowed && handled) /new module handled the request but not authorized keep trying
        //if (allowed && handled) //new module allowed but keep trying in case someone denies.
            
        if (!allowed && !handled)  //old module break on !allowed
        {   
            debug_printf("RTSPSession.cpp::Run(kAuthorizingRequest)  skipping other modules fCurrentModule = %lu numModules=%lu\n", x,numModules);
            break;
        }
    }
    
    // outAuthRealm is set to the realm that is given by the module that has denied authentication
    StrPtrLen* realm = request->GetValue(qtssRTSPReqURLRealm);
    *outAuthRealm = realm->GetAsCString();
    
    return theErr;
}
示例#21
0
QTSS_Error  QTSSCallbacks::QTSS_Authenticate(const char* inAuthUserName, const char* inAuthResourceLocalPath, const char* inAuthMoviesDir, QTSS_ActionFlags inAuthRequestAction, QTSS_AuthScheme inAuthScheme, QTSS_RTSPRequestObject ioAuthRequestObject)
{
    if((inAuthUserName == NULL) || (inAuthResourceLocalPath == NULL) || (inAuthMoviesDir == NULL) || (ioAuthRequestObject == NULL)) 
        return QTSS_BadArgument;
    if(inAuthRequestAction == qtssActionFlagsNoFlags)
        return QTSS_BadArgument;
    if(inAuthScheme == qtssAuthNone)
        return QTSS_BadArgument;

    // First create a RTSPRequestInterface object 
    // There is no session attached to it, so just pass in NULL for the RTSPSession
    RTSPRequestInterface *request =  (RTSPRequestInterface *) ioAuthRequestObject;
    // Set all the attributes required by the authentication module, using the input values
    (void) request->SetValue(qtssRTSPReqUserName, 0,  inAuthUserName , ::strlen(inAuthUserName), QTSSDictionary::kDontObeyReadOnly);
    (void) request->SetValue(qtssRTSPReqLocalPath, 0,  inAuthResourceLocalPath , ::strlen(inAuthResourceLocalPath), QTSSDictionary::kDontObeyReadOnly);
    (void) request->SetValue(qtssRTSPReqRootDir, 0,  inAuthMoviesDir , ::strlen(inAuthMoviesDir), QTSSDictionary::kNoFlags);
    (void) request->SetValue(qtssRTSPReqAction, 0,  (const void *)&inAuthRequestAction , sizeof(QTSS_ActionFlags), QTSSDictionary::kNoFlags);
    (void) request->SetValue(qtssRTSPReqAuthScheme, 0,  (const void *)&inAuthScheme , sizeof(QTSS_AuthScheme), QTSSDictionary::kDontObeyReadOnly);
    QTSSUserProfile *profile = request->GetUserProfile();
    (void) profile->SetValue(qtssUserName, 0, inAuthUserName, ::strlen(inAuthUserName), QTSSDictionary::kDontObeyReadOnly);
    
    
    // Because this is a role being executed from inside a callback, we need to
    // make sure that QTSS_RequestEvent will not work.
    Task* curTask = NULL;
    QTSS_ModuleState* theState = (QTSS_ModuleState*)OSThread::GetMainThreadData();
    if (OSThread::GetCurrent() != NULL)
        theState = (QTSS_ModuleState*)OSThread::GetCurrent()->GetThreadData();
        
    if (theState != NULL)
        curTask = theState->curTask;
    
    // Setup the authentication param block
    QTSS_RoleParams theAuthenticationParams;
    theAuthenticationParams.rtspAthnParams.inRTSPRequest = request;
            
    QTSS_Error theErr = QTSS_RequestFailed;
    
    UInt32 x = 0;
    UInt32 numModules = QTSServerInterface::GetNumModulesInRole(QTSSModule::kRTSPAthnRole);
    QTSSModule* theModulePtr = NULL;
    Bool16 allowedDefault = QTSServerInterface::GetServer()->GetPrefs()->GetAllowGuestDefault();
    Bool16 allowed = allowedDefault; //server pref?
    Bool16 hasUser = false; 
    Bool16 handled = false;
    
    
    // Call all the modules that are registered for the RTSP Authorize Role 
    for ( ; x < numModules; x++)
    {
        request->SetAllowed(allowedDefault);  
        request->SetHasUser(false);
        request->SetAuthHandled(false);
    
        debug_printf(" QTSSCallbacks::QTSS_Authenticate calling module module = %lu numModules=%lu\n", x,numModules);
        theModulePtr = QTSServerInterface::GetModule(QTSSModule::kRTSPAthnRole, x);
        theErr =  QTSS_NoErr;
        if (theModulePtr)
        {    
            theErr = theModulePtr->CallDispatch(QTSS_RTSPAuthenticate_Role, &theAuthenticationParams);
            debug_printf(" QTSSCallbacks::QTSS_Authorize calling module module = %lu numModules=%lu ModuleError=%ld\n", x,numModules, theErr);
        }
        else
        {   
            debug_printf(" QTSSCallbacks::QTSS_Authorize calling module module = %lu is NULL! numModules=%lu\n", x,numModules);
            continue;
        }
        allowed = request->GetAllowed();
        hasUser = request->GetHasUser();
        handled = request->GetAuthHandled();
        debug_printf("QTSSCallbacks::QTSS_Authenticate allowedDefault =%d allowed= %d hasUser = %d handled=%d \n",allowedDefault, allowed,hasUser, handled);
      
                  
        if (hasUser || handled ) //See RTSPSession.cpp::Run state=kAuthenticatingRequest
        {   
            debug_printf(" QTSSCallbacks::QTSS_Authenticate skipping other modules fCurrentModule = %lu numModules=%lu\n", x,numModules);
            break;
        }
    }

    
    // Reset the curTask to what it was before this role started
    if (theState != NULL)
        theState->curTask = curTask;

    return theErr;
}
示例#22
0
QTSS_Error QTSServer::RereadPrefsService(QTSS_ServiceFunctionArgsPtr /*inArgs*/)
{
    //
    // This function can only be called safely when the server is completely running.
    // Ensuring this is a bit complicated because of preemption. Here's how it's done...
    
    QTSServerInterface* theServer = QTSServerInterface::GetServer();
    
    // This is to make sure this function isn't being called before the server is
    // completely started up.
    if ((theServer == NULL) || (theServer->GetServerState() != qtssRunningState))
        return QTSS_OutOfState;

    // Because the server must have started up, and because this object always stays
    // around (until the process dies), we can now safely get this object.
    QTSServerPrefs* thePrefs = theServer->GetPrefs();
    
    // Grab the prefs mutex. We want to make sure that calls to RereadPrefsService
    // are serialized. This also prevents the server from shutting down while in
    // this function, because the QTSServer destructor grabs this mutex as well.
    OSMutexLocker locker(thePrefs->GetMutex());
    
    // Finally, check the server state again. The state may have changed
    // to qtssShuttingDownState or qtssFatalErrorState in this time, though
    // at this point we have the prefs mutex, so we are guarenteed that the
    // server can't actually shut down anymore
    if (theServer->GetServerState() != qtssRunningState)
        return QTSS_OutOfState;
    
    // Ok, we're ready to reread preferences now.
    
    //
    // Reread preferences
    sPrefsSource->Parse();
    thePrefs->RereadServerPreferences(true);
    
    // Delete all the streams
    QTSSModule** theModule = NULL;
    UInt32 theLen = 0;
    
    for (int y = 0; QTSServerInterface::GetServer()->GetValuePtr(qtssSvrModuleObjects, y, (void**)&theModule, &theLen) == QTSS_NoErr; y++)
    {
        Assert(theModule != NULL);
        Assert(theLen == sizeof(QTSSModule*));
        
        (*theModule)->GetPrefsDict()->RereadPreferences();

#if DEBUG
        theModule = NULL;
        theLen = 0;
#endif
    }
    
    //
    // Go through each module's prefs object and have those reread as well

    //
    // Now that we are done rereading the prefs, invoke all modules in the RereadPrefs
    // role so they can update their internal prefs caches.
    for (UInt32 x = 0; x < QTSServerInterface::GetNumModulesInRole(QTSSModule::kRereadPrefsRole); x++)
    {
        QTSSModule* theModule = QTSServerInterface::GetModule(QTSSModule::kRereadPrefsRole, x);
        (void)theModule->CallDispatch(QTSS_RereadPrefs_Role, NULL);
    }
    return QTSS_NoErr;
}