diff --git a/windows/JackWinNamedPipe.cpp b/windows/JackWinNamedPipe.cpp index eb7ccc8d..9fec3d3f 100644 --- a/windows/JackWinNamedPipe.cpp +++ b/windows/JackWinNamedPipe.cpp @@ -52,6 +52,59 @@ int JackWinNamedPipe::Write(void* data, int len) } } +/* +See : + http://answers.google.com/answers/threadview?id=430173 + http://msdn.microsoft.com/en-us/library/windows/desktop/aa365800(v=vs.85).aspx +*/ + +int JackWinNamedPipeClient::ConnectAux(int retry_count) +{ + jack_log("Connect: fName %s", fName); + + while (true) { + + fNamedPipe = CreateFile(fName, // pipe name + GENERIC_READ | // read and write access + GENERIC_WRITE, + 0, // no sharing + NULL, // default security attributes + OPEN_EXISTING, // opens existing pipe + 0, // default attributes + NULL); // no template file + + // Break if the pipe handle is valid. + if (fNamedPipe != INVALID_HANDLE_VALUE) { + return 0; + } + + // Exit if an error other than ERROR_PIPE_BUSY occurs. + if (GetLastError() != ERROR_PIPE_BUSY) { + jack_error("Cannot connect to named pipe = %s err = %ld", fName, GetLastError()); + return -1; + } + + // All pipe instances are busy, so wait for 2 seconds. + if (!WaitNamedPipe(lpszPipename, 2000)) { + jack_error("Cannot connect to named pipe = %s err = %ld", fName, GetLastError()); + return -1; + } + } +} + +int JackWinNamedPipeClient::Connect(const char* dir, int which) +{ + snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%d", dir, which); + return ConnectAux(); +} + +int JackWinNamedPipeClient::Connect(const char* dir, const char* name, int which) +{ + snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%s_%d", dir, name, which); + return ConnectAux(); +} + +/* int JackWinNamedPipeClient::Connect(const char* dir, int which) { snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%d", dir, which); @@ -95,6 +148,7 @@ int JackWinNamedPipeClient::Connect(const char* dir, const char* name, int which return 0; } } +*/ int JackWinNamedPipeClient::Close() { @@ -131,8 +185,9 @@ JackWinAsyncNamedPipeClient::JackWinAsyncNamedPipeClient(HANDLE pipe, bool pendi TRUE, // initial state = signaled NULL); // unnamed event object - if (!fPendingIO) + if (!fPendingIO) { SetEvent(fOverlap.hEvent); + } fIOState = (fPendingIO) ? kConnecting : kReading; } @@ -188,7 +243,6 @@ int JackWinAsyncNamedPipeClient::Read(void* data, int len) DWORD read; jack_log("JackWinNamedPipeClient::Read len = %ld", len); BOOL res = ReadFile(fNamedPipe, data, len, &read, &fOverlap); - jack_log("JackWinNamedPipeClient::Read res = %ld read %ld", res, read); if (res && read != 0) { fPendingIO = false; @@ -224,6 +278,40 @@ int JackWinAsyncNamedPipeClient::Write(void* data, int len) // Server side +int JackWinNamedPipeServer::BindAux() +{ + jack_log("Bind: fName %s", fName); + + if ((fNamedPipe = CreateNamedPipe(fName, + 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 + INFINITE, // client time-out + NULL)) == INVALID_HANDLE_VALUE) { // no security + jack_error("Cannot bind server to pipe err = %ld", GetLastError()); + return -1; + } else { + return 0; + } +} + +int JackWinNamedPipeServer::Bind(const char* dir, int which) +{ + snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%d", dir, which); + return BindAux(); +} + +int JackWinNamedPipeServer::Bind(const char* dir, const char* name, int which) +{ + snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%s_%d", dir, name, which); + return BindAux(); +} + +/* int JackWinNamedPipeServer::Bind(const char* dir, int which) { snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%d", dir, which); @@ -267,6 +355,7 @@ int JackWinNamedPipeServer::Bind(const char* dir, const char* name, int which) return 0; } } +*/ bool JackWinNamedPipeServer::Accept() { @@ -320,6 +409,40 @@ int JackWinNamedPipeServer::Close() // Server side +int JackWinAsyncNamedPipeServer::BindAux() +{ + jack_log("Bind: fName %s", fName); + + if ((fNamedPipe = CreateNamedPipe(fName, + PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED, // 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 + INFINITE, // client time-out + NULL)) == INVALID_HANDLE_VALUE) { // no security a + jack_error("Cannot bind server to pipe err = %ld", GetLastError()); + return -1; + } else { + return 0; + } +} + +int JackWinAsyncNamedPipeServer::Bind(const char* dir, int which) +{ + snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%d", dir, which); + return BindAux(); +} + +int JackWinAsyncNamedPipeServer::Bind(const char* dir, const char* name, int which) +{ + snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%s_%d", dir, name, which); + return BindAux(); +} + +/* int JackWinAsyncNamedPipeServer::Bind(const char* dir, int which) { snprintf(fName, sizeof(fName), "\\\\.\\pipe\\%s_jack_%d", dir, which); @@ -363,6 +486,7 @@ int JackWinAsyncNamedPipeServer::Bind(const char* dir, const char* name, int whi return 0; } } +*/ bool JackWinAsyncNamedPipeServer::Accept() { @@ -383,7 +507,7 @@ JackWinNamedPipeClient* JackWinAsyncNamedPipeServer::AcceptClient() return new JackWinAsyncNamedPipeClient(fNamedPipe, false); default: - jack_error("Cannot connect server pipe name = %s err = %ld", fName, GetLastError()); + jack_error("Cannot connect server pipe name = %s err = %ld", fName, GetLastError()); return NULL; break; } diff --git a/windows/JackWinNamedPipe.h b/windows/JackWinNamedPipe.h index 6487d4b3..fecf3a6f 100644 --- a/windows/JackWinNamedPipe.h +++ b/windows/JackWinNamedPipe.h @@ -1,20 +1,20 @@ /* Copyright (C) 2004-2008 Grame - + This program is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. - + This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. - + You should have received a copy of the GNU Lesser General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - + */ @@ -54,6 +54,10 @@ class JackWinNamedPipe class JackWinNamedPipeClient : public JackWinNamedPipe { + private: + + int ConnectAux(); + public: JackWinNamedPipeClient(): JackWinNamedPipe() @@ -114,6 +118,9 @@ class JackWinAsyncNamedPipeClient : public JackWinNamedPipeClient class JackWinNamedPipeServer : public JackWinNamedPipe { + private: + + int BindAux(); public: @@ -136,6 +143,10 @@ class JackWinNamedPipeServer : public JackWinNamedPipe class JackWinAsyncNamedPipeServer : public JackWinNamedPipeServer { + private: + + int BindAux(); + public: JackWinAsyncNamedPipeServer(): JackWinNamedPipeServer()