Esempio n. 1
0
bool CRemoteCacheLink::EnsurePipeOpen()
{
	AutoLocker lock(m_critSec);

	if (InternalEnsurePipeOpen (m_hPipe, GetCachePipeName()))
	{
		// create an unnamed (=local) manual reset event for use in the overlapped structure
		if (m_hEvent)
			return true;

		m_hEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
		if (m_hEvent)
			return true;

		CTraceToOutputDebugString::Instance()(__FUNCTION__ ": CreateEvent failed");
		ClosePipe();
	}

	return false;
}
Esempio n. 2
0
bool CCacheDlg::EnsurePipeOpen()
{
	if(m_hPipe != INVALID_HANDLE_VALUE)
	{
		return true;
	}

	m_hPipe = CreateFile(
		GetCachePipeName(),   // pipe name
		GENERIC_READ |					// read and write access
		GENERIC_WRITE,
		0,								// no sharing
		nullptr,						// default security attributes
		OPEN_EXISTING,				// opens existing pipe
		FILE_FLAG_OVERLAPPED,			// default attributes
		nullptr);						// no template file

	if (m_hPipe == INVALID_HANDLE_VALUE && GetLastError() == ERROR_PIPE_BUSY)
	{
		// TSVNCache is running but is busy connecting a different client.
		// Do not give up immediately but wait for a few milliseconds until
		// the server has created the next pipe instance
		if (WaitNamedPipe(GetCachePipeName(), 50))
		{
			m_hPipe = CreateFile(
				GetCachePipeName(),   // pipe name
				GENERIC_READ |					// read and write access
				GENERIC_WRITE,
				0,								// no sharing
				nullptr,						// default security attributes
				OPEN_EXISTING,				// opens existing pipe
				FILE_FLAG_OVERLAPPED,			// default attributes
				nullptr);						// no template file
		}
	}


	if (m_hPipe != INVALID_HANDLE_VALUE)
	{
		// The pipe connected; change to message-read mode.
		DWORD dwMode;

		dwMode = PIPE_READMODE_MESSAGE;
		if(!SetNamedPipeHandleState(
			m_hPipe,    // pipe handle
			&dwMode,  // new pipe mode
			nullptr,  // don't set maximum bytes
			nullptr)) // don't set maximum time
		{
			ATLTRACE("SetNamedPipeHandleState failed");
			CloseHandle(m_hPipe);
			m_hPipe = INVALID_HANDLE_VALUE;
			return false;
		}
		// create an unnamed (=local) manual reset event for use in the overlapped structure
		m_hEvent = CreateEvent(nullptr, TRUE, FALSE, nullptr);
		if (m_hEvent)
			return true;
		ATLTRACE("CreateEvent failed");
		ClosePipe();
		return false;
	}

	return false;
}
Esempio n. 3
0
DWORD WINAPI PipeThread(LPVOID lpvParam)
{
	ATLTRACE("PipeThread started\n");
	bool * bRun = (bool *)lpvParam;
	// The main loop creates an instance of the named pipe and
	// then waits for a client to connect to it. When the client
	// connects, a thread is created to handle communications
	// with that client, and the loop is repeated.
	DWORD dwThreadId;
	BOOL fConnected;
	CAutoFile hPipe;

	while (*bRun)
	{
		hPipe = CreateNamedPipe(
			GetCachePipeName(),
			PIPE_ACCESS_DUPLEX,       // read/write access
			PIPE_TYPE_MESSAGE |       // message type pipe
			PIPE_READMODE_MESSAGE |   // message-read mode
			PIPE_WAIT,                // blocking mode
			PIPE_UNLIMITED_INSTANCES, // max. instances
			BUFSIZE,                  // output buffer size
			BUFSIZE,                  // input buffer size
			NMPWAIT_USE_DEFAULT_WAIT, // client time-out
			NULL);					  // NULL DACL

		if (!hPipe)
		{
			//OutputDebugStringA("TSVNCache: CreatePipe failed\n");
			//DebugOutputLastError();
			if (*bRun)
				Sleep(200);
			continue; // never leave the thread!
		}

		// Wait for the client to connect; if it succeeds,
		// the function returns a nonzero value. If the function returns
		// zero, GetLastError returns ERROR_PIPE_CONNECTED.
		fConnected = ConnectNamedPipe(hPipe, NULL) ? TRUE : (GetLastError() == ERROR_PIPE_CONNECTED);
		if (fConnected)
		{
			// Create a thread for this client.
			CAutoGeneralHandle hInstanceThread = CreateThread(
				NULL,              // no security attribute
				0,                 // default stack size
				InstanceThread,
				(HANDLE) hPipe,    // thread parameter
				0,                 // not suspended
				&dwThreadId);      // returns thread ID

			if (!hInstanceThread)
			{
				//OutputDebugStringA("TSVNCache: Could not create Instance thread\n");
				//DebugOutputLastError();
				DisconnectNamedPipe(hPipe);
				// since we're now closing this thread, we also have to close the whole application!
				// otherwise the thread is dead, but the app is still running, refusing new instances
				// but no pipe will be available anymore.
				PostMessage(hWnd, WM_CLOSE, 0, 0);
				return 1;
			}
			// detach the handle, since we passed it to the thread
			hPipe.Detach();
		}
		else
		{
			// The client could not connect, so close the pipe.
			//OutputDebugStringA("TSVNCache: ConnectNamedPipe failed\n");
			//DebugOutputLastError();
			hPipe.CloseHandle();
			if (*bRun)
				Sleep(200);
			continue;	// don't end the thread!
		}
	}
	ATLTRACE("Pipe thread exited\n");
	return 0;
}