| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "ipc/ipc_channel_win.h" | 5 #include "ipc/ipc_channel_win.h" |
| 6 | 6 |
| 7 #include <windows.h> | 7 #include <windows.h> |
| 8 | 8 |
| 9 #include "base/auto_reset.h" | 9 #include "base/auto_reset.h" |
| 10 #include "base/bind.h" | 10 #include "base/bind.h" |
| 11 #include "base/compiler_specific.h" | 11 #include "base/compiler_specific.h" |
| (...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 107 // static | 107 // static |
| 108 const std::wstring Channel::ChannelImpl::PipeName( | 108 const std::wstring Channel::ChannelImpl::PipeName( |
| 109 const std::string& channel_id) { | 109 const std::string& channel_id) { |
| 110 std::string name("\\\\.\\pipe\\chrome."); | 110 std::string name("\\\\.\\pipe\\chrome."); |
| 111 return ASCIIToWide(name.append(channel_id)); | 111 return ASCIIToWide(name.append(channel_id)); |
| 112 } | 112 } |
| 113 | 113 |
| 114 bool Channel::ChannelImpl::CreatePipe(const IPC::ChannelHandle &channel_handle, | 114 bool Channel::ChannelImpl::CreatePipe(const IPC::ChannelHandle &channel_handle, |
| 115 Mode mode) { | 115 Mode mode) { |
| 116 DCHECK_EQ(INVALID_HANDLE_VALUE, pipe_); | 116 DCHECK_EQ(INVALID_HANDLE_VALUE, pipe_); |
| 117 const std::wstring pipe_name = PipeName(channel_handle.name); | 117 string16 pipe_name; |
| 118 if (mode & MODE_SERVER_FLAG) { | 118 // If we already have a valid pipe for channel just copy it. |
| 119 if (channel_handle.pipe.handle) { |
| 120 DCHECK(channel_handle.name.empty()); |
| 121 pipe_name = L"Not Available"; // Just used for LOG |
| 122 // Check that the given pipe confirms to the specified mode. We can |
| 123 // only check for PIPE_TYPE_MESSAGE & PIPE_SERVER_END flags since the |
| 124 // other flags (PIPE_TYPE_BYTE, and PIPE_CLIENT_END) are defined as 0. |
| 125 DWORD flags = 0; |
| 126 GetNamedPipeInfo(channel_handle.pipe.handle, &flags, NULL, NULL, NULL); |
| 127 DCHECK(!(flags & PIPE_TYPE_MESSAGE)); |
| 128 if (((mode & MODE_SERVER_FLAG) && !(flags & PIPE_SERVER_END)) || |
| 129 ((mode & MODE_CLIENT_FLAG) && (flags & PIPE_SERVER_END))) { |
| 130 LOG(WARNING) << "Inconsistent open mode. Mode :" << mode; |
| 131 return false; |
| 132 } |
| 133 if (!DuplicateHandle(GetCurrentProcess(), |
| 134 channel_handle.pipe.handle, |
| 135 GetCurrentProcess(), |
| 136 &pipe_, |
| 137 0, |
| 138 FALSE, |
| 139 DUPLICATE_SAME_ACCESS)) { |
| 140 LOG(WARNING) << "DuplicateHandle failed. Error :" << GetLastError(); |
| 141 return false; |
| 142 } |
| 143 } else if (mode & MODE_SERVER_FLAG) { |
| 144 DCHECK(!channel_handle.pipe.handle); |
| 145 const DWORD open_mode = PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED | |
| 146 FILE_FLAG_FIRST_PIPE_INSTANCE; |
| 147 pipe_name = PipeName(channel_handle.name); |
| 119 pipe_ = CreateNamedPipeW(pipe_name.c_str(), | 148 pipe_ = CreateNamedPipeW(pipe_name.c_str(), |
| 120 PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED | | 149 open_mode, |
| 121 FILE_FLAG_FIRST_PIPE_INSTANCE, | |
| 122 PIPE_TYPE_BYTE | PIPE_READMODE_BYTE, | 150 PIPE_TYPE_BYTE | PIPE_READMODE_BYTE, |
| 123 1, | 151 1, |
| 124 Channel::kReadBufferSize, | 152 Channel::kReadBufferSize, |
| 125 Channel::kReadBufferSize, | 153 Channel::kReadBufferSize, |
| 126 5000, | 154 5000, |
| 127 NULL); | 155 NULL); |
| 128 } else if (mode & MODE_CLIENT_FLAG) { | 156 } else if (mode & MODE_CLIENT_FLAG) { |
| 157 DCHECK(!channel_handle.pipe.handle); |
| 158 pipe_name = PipeName(channel_handle.name); |
| 129 pipe_ = CreateFileW(pipe_name.c_str(), | 159 pipe_ = CreateFileW(pipe_name.c_str(), |
| 130 GENERIC_READ | GENERIC_WRITE, | 160 GENERIC_READ | GENERIC_WRITE, |
| 131 0, | 161 0, |
| 132 NULL, | 162 NULL, |
| 133 OPEN_EXISTING, | 163 OPEN_EXISTING, |
| 134 SECURITY_SQOS_PRESENT | SECURITY_IDENTIFICATION | | 164 SECURITY_SQOS_PRESENT | SECURITY_IDENTIFICATION | |
| 135 FILE_FLAG_OVERLAPPED, | 165 FILE_FLAG_OVERLAPPED, |
| 136 NULL); | 166 NULL); |
| 137 } else { | 167 } else { |
| 138 NOTREACHED(); | 168 NOTREACHED(); |
| 139 } | 169 } |
| 170 |
| 140 if (pipe_ == INVALID_HANDLE_VALUE) { | 171 if (pipe_ == INVALID_HANDLE_VALUE) { |
| 141 // If this process is being closed, the pipe may be gone already. | 172 // If this process is being closed, the pipe may be gone already. |
| 142 LOG(WARNING) << "Unable to create pipe \"" << pipe_name << | 173 LOG(WARNING) << "Unable to create pipe \"" << pipe_name << |
| 143 "\" in " << (mode == 0 ? "server" : "client") | 174 "\" in " << (mode == 0 ? "server" : "client") |
| 144 << " mode. Error :" << GetLastError(); | 175 << " mode. Error :" << GetLastError(); |
| 145 return false; | 176 return false; |
| 146 } | 177 } |
| 147 | 178 |
| 148 // Create the Hello message to be sent when Connect is called | 179 // Create the Hello message to be sent when Connect is called |
| 149 scoped_ptr<Message> m(new Message(MSG_ROUTING_NONE, | 180 scoped_ptr<Message> m(new Message(MSG_ROUTING_NONE, |
| (...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 424 bool Channel::Send(Message* message) { | 455 bool Channel::Send(Message* message) { |
| 425 return channel_impl_->Send(message); | 456 return channel_impl_->Send(message); |
| 426 } | 457 } |
| 427 | 458 |
| 428 // static | 459 // static |
| 429 bool Channel::IsNamedServerInitialized(const std::string& channel_id) { | 460 bool Channel::IsNamedServerInitialized(const std::string& channel_id) { |
| 430 return ChannelImpl::IsNamedServerInitialized(channel_id); | 461 return ChannelImpl::IsNamedServerInitialized(channel_id); |
| 431 } | 462 } |
| 432 | 463 |
| 433 } // namespace IPC | 464 } // namespace IPC |
| OLD | NEW |