Пример #1
0
static Symbol* fkt_begin_critical(const std::vector<Symbol*>& vecSyms,
	ParseInfo& info, RuntimeInfo &runinfo, SymbolTable* pSymTab)
{
	// no argument given: lock global mutex
	if(vecSyms.size() == 0)
	{
		info.pmutexGlobal->lock();
	}
	else
	{
		for(Symbol* pSym : vecSyms)
		{
			if(pSym->GetType() == SYMBOL_ARRAY)
				fkt_begin_critical(((SymbolArray*)pSym)->GetArr(), info, runinfo, pSymTab);
			else if(pSym->GetType() == SYMBOL_INT)
			{
				//std::lock_guard<std::mutex> lck(*info.pmutexCrit);

				int iHandle = pSym->GetValInt();
				Handle *pHandle = info.phandles->GetHandle(iHandle);

				if(pHandle==0 || pHandle->GetType()!=HANDLE_MUTEX)
				{
					std::ostringstream ostrErr;
					ostrErr << linenr(runinfo) << "Handle (" 
						<< iHandle << ") does not exist"
						<< " or is not a mutex handle. Ignoring." 
						<< std::endl;
					throw tl::Err(ostrErr.str(), 0);
					//continue;
				}

				std::mutex *pMutex = ((HandleMutex*)pHandle)->GetInternalHandle();
				pMutex->lock();
			}
			else
			{
				std::ostringstream ostrErr;
				ostrErr << linenr(runinfo) << "Invalid mutex handle: "
						<< pSym->print() << " Ignoring." << std::endl;
				throw tl::Err(ostrErr.str(), 0);
			}
		}
	}

	return 0;
}
Пример #2
0
static Symbol* fkt_thread_join(const std::vector<Symbol*>& vecSyms,
	ParseInfo& info, RuntimeInfo &runinfo, SymbolTable* pSymTab)
{
	if(vecSyms.size()<1)
	{
		std::ostringstream ostrErr;
		ostrErr << linenr(runinfo) << "join needs at least one argument." << std::endl;
		throw tl::Err(ostrErr.str(),0);
	}

	Symbol *pRet = 0;
	for(Symbol* pSym : vecSyms)
	{
		if(pSym == 0) continue;

		if(pSym->GetType() == SYMBOL_ARRAY)
		{
			return fkt_thread_join(((SymbolArray*)pSym)->GetArr(), info, runinfo, pSymTab);
		}

		if(pSym->GetType() != SYMBOL_INT)
		{
			std::ostringstream ostrErr;
			ostrErr << linenr(runinfo) << "join needs thread handles." << std::endl;
			throw tl::Err(ostrErr.str(), 0);
			//continue;
		}

		t_int iHandle = ((SymbolInt*)pSym)->GetVal();
		Handle *pHandle = info.phandles->GetHandle(iHandle);

		if(pHandle==0)
		{
			std::ostringstream ostrErr;
			ostrErr << linenr(runinfo) << "Handle (" 
				<< iHandle << ") does not exist." << std::endl;
			throw tl::Err(ostrErr.str(), 0);
			//continue;
		}

		if(pHandle->GetType() == HANDLE_THREAD)
		{
			HandleThread *pThreadHandle = (HandleThread*)pHandle;
			std::thread *pThread = pThreadHandle->GetInternalHandle();

			//log_debug("Joining thread ", pThread, "...");
			pThread->join();
			//log_debug("Joined thread ", pThread, ".");
		}
		else if(pHandle->GetType() == HANDLE_TASK)
		{
			HandleTask *pTaskHandle = (HandleTask*)pHandle;
			std::future<Symbol*> *pFut = pTaskHandle->GetInternalHandle();

			// TODO: array task joins
			if(pRet != 0)
				delete pRet;
			pRet = pFut->get();
		}
		else
		{
			std::ostringstream ostrErr;
			ostrErr << linenr(runinfo) << "Handle (" 
				<< iHandle << ") is invalid." << std::endl;
			throw tl::Err(ostrErr.str(), 0);
		}
		
		info.phandles->CloseHandle(iHandle);
	}

	return pRet;
}