ipc/chromium/src/chrome/common/ipc_channel_posix.h

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

michael@0 1 // Copyright (c) 2008 The Chromium Authors. All rights reserved.
michael@0 2 // Use of this source code is governed by a BSD-style license that can be
michael@0 3 // found in the LICENSE file.
michael@0 4
michael@0 5 #ifndef CHROME_COMMON_IPC_CHANNEL_POSIX_H_
michael@0 6 #define CHROME_COMMON_IPC_CHANNEL_POSIX_H_
michael@0 7
michael@0 8 #include "chrome/common/ipc_channel.h"
michael@0 9
michael@0 10 #include <sys/socket.h> // for CMSG macros
michael@0 11
michael@0 12 #include <queue>
michael@0 13 #include <string>
michael@0 14 #include <vector>
michael@0 15 #include <list>
michael@0 16
michael@0 17 #include "base/message_loop.h"
michael@0 18 #include "chrome/common/file_descriptor_set_posix.h"
michael@0 19
michael@0 20 namespace IPC {
michael@0 21
michael@0 22 // An implementation of ChannelImpl for POSIX systems that works via
michael@0 23 // socketpairs. See the .cc file for an overview of the implementation.
michael@0 24 class Channel::ChannelImpl : public MessageLoopForIO::Watcher {
michael@0 25 public:
michael@0 26 // Mirror methods of Channel, see ipc_channel.h for description.
michael@0 27 ChannelImpl(const std::wstring& channel_id, Mode mode, Listener* listener);
michael@0 28 ChannelImpl(int fd, Mode mode, Listener* listener);
michael@0 29 ~ChannelImpl() { Close(); }
michael@0 30 bool Connect();
michael@0 31 void Close();
michael@0 32 Listener* set_listener(Listener* listener) {
michael@0 33 Listener* old = listener_;
michael@0 34 listener_ = listener;
michael@0 35 return old;
michael@0 36 }
michael@0 37 bool Send(Message* message);
michael@0 38 void GetClientFileDescriptorMapping(int *src_fd, int *dest_fd) const;
michael@0 39
michael@0 40 void ResetFileDescriptor(int fd);
michael@0 41
michael@0 42 int GetFileDescriptor() const {
michael@0 43 return pipe_;
michael@0 44 }
michael@0 45 void CloseClientFileDescriptor();
michael@0 46
michael@0 47 // See the comment in ipc_channel.h for info on Unsound_IsClosed() and
michael@0 48 // Unsound_NumQueuedMessages().
michael@0 49 bool Unsound_IsClosed() const;
michael@0 50 uint32_t Unsound_NumQueuedMessages() const;
michael@0 51
michael@0 52 private:
michael@0 53 void Init(Mode mode, Listener* listener);
michael@0 54 bool CreatePipe(const std::wstring& channel_id, Mode mode);
michael@0 55 bool EnqueueHelloMessage();
michael@0 56
michael@0 57 bool ProcessIncomingMessages();
michael@0 58 bool ProcessOutgoingMessages();
michael@0 59
michael@0 60 // MessageLoopForIO::Watcher implementation.
michael@0 61 virtual void OnFileCanReadWithoutBlocking(int fd);
michael@0 62 virtual void OnFileCanWriteWithoutBlocking(int fd);
michael@0 63
michael@0 64 #if defined(OS_MACOSX)
michael@0 65 void CloseDescriptors(uint32_t pending_fd_id);
michael@0 66 #endif
michael@0 67
michael@0 68 void OutputQueuePush(Message* msg);
michael@0 69 void OutputQueuePop();
michael@0 70
michael@0 71 Mode mode_;
michael@0 72
michael@0 73 // After accepting one client connection on our server socket we want to
michael@0 74 // stop listening.
michael@0 75 MessageLoopForIO::FileDescriptorWatcher server_listen_connection_watcher_;
michael@0 76 MessageLoopForIO::FileDescriptorWatcher read_watcher_;
michael@0 77 MessageLoopForIO::FileDescriptorWatcher write_watcher_;
michael@0 78
michael@0 79 // Indicates whether we're currently blocked waiting for a write to complete.
michael@0 80 bool is_blocked_on_write_;
michael@0 81
michael@0 82 // If sending a message blocks then we use this variable
michael@0 83 // to keep track of where we are.
michael@0 84 size_t message_send_bytes_written_;
michael@0 85
michael@0 86 // If the kTestingChannelID flag is specified, we use a FIFO instead of
michael@0 87 // a socketpair().
michael@0 88 bool uses_fifo_;
michael@0 89
michael@0 90 int server_listen_pipe_;
michael@0 91 int pipe_;
michael@0 92 int client_pipe_; // The client end of our socketpair().
michael@0 93
michael@0 94 // The "name" of our pipe. On Windows this is the global identifier for
michael@0 95 // the pipe. On POSIX it's used as a key in a local map of file descriptors.
michael@0 96 std::string pipe_name_;
michael@0 97
michael@0 98 Listener* listener_;
michael@0 99
michael@0 100 // Messages to be sent are queued here.
michael@0 101 std::queue<Message*> output_queue_;
michael@0 102
michael@0 103 // We read from the pipe into this buffer
michael@0 104 char input_buf_[Channel::kReadBufferSize];
michael@0 105
michael@0 106 enum {
michael@0 107 // We assume a worst case: kReadBufferSize bytes of messages, where each
michael@0 108 // message has no payload and a full complement of descriptors.
michael@0 109 MAX_READ_FDS = (Channel::kReadBufferSize / sizeof(IPC::Message::Header)) *
michael@0 110 FileDescriptorSet::MAX_DESCRIPTORS_PER_MESSAGE
michael@0 111 };
michael@0 112
michael@0 113 // This is a control message buffer large enough to hold kMaxReadFDs
michael@0 114 #if defined(OS_MACOSX) || defined(OS_NETBSD)
michael@0 115 // TODO(agl): OSX appears to have non-constant CMSG macros!
michael@0 116 char input_cmsg_buf_[1024];
michael@0 117 #else
michael@0 118 char input_cmsg_buf_[CMSG_SPACE(sizeof(int) * MAX_READ_FDS)];
michael@0 119 #endif
michael@0 120
michael@0 121 // Large messages that span multiple pipe buffers, get built-up using
michael@0 122 // this buffer.
michael@0 123 std::string input_overflow_buf_;
michael@0 124 std::vector<int> input_overflow_fds_;
michael@0 125
michael@0 126 // In server-mode, we have to wait for the client to connect before we
michael@0 127 // can begin reading. We make use of the input_state_ when performing
michael@0 128 // the connect operation in overlapped mode.
michael@0 129 bool waiting_connect_;
michael@0 130
michael@0 131 // This flag is set when processing incoming messages. It is used to
michael@0 132 // avoid recursing through ProcessIncomingMessages, which could cause
michael@0 133 // problems. TODO(darin): make this unnecessary
michael@0 134 bool processing_incoming_;
michael@0 135
michael@0 136 // This flag is set after we've closed the channel.
michael@0 137 bool closed_;
michael@0 138
michael@0 139 #if defined(OS_MACOSX)
michael@0 140 struct PendingDescriptors {
michael@0 141 uint32_t id;
michael@0 142 scoped_refptr<FileDescriptorSet> fds;
michael@0 143
michael@0 144 PendingDescriptors() : id(0) { }
michael@0 145 PendingDescriptors(uint32_t id, FileDescriptorSet *fds)
michael@0 146 : id(id),
michael@0 147 fds(fds)
michael@0 148 { }
michael@0 149 };
michael@0 150
michael@0 151 std::list<PendingDescriptors> pending_fds_;
michael@0 152
michael@0 153 // A generation ID for RECEIVED_FD messages.
michael@0 154 uint32_t last_pending_fd_id_;
michael@0 155 #endif
michael@0 156
michael@0 157 // This variable is updated so it matches output_queue_.size(), except we can
michael@0 158 // read output_queue_length_ from any thread (if we're OK getting an
michael@0 159 // occasional out-of-date or bogus value). We use output_queue_length_ to
michael@0 160 // implement Unsound_NumQueuedMessages.
michael@0 161 size_t output_queue_length_;
michael@0 162
michael@0 163 ScopedRunnableMethodFactory<ChannelImpl> factory_;
michael@0 164
michael@0 165 DISALLOW_COPY_AND_ASSIGN(ChannelImpl);
michael@0 166 };
michael@0 167
michael@0 168 } // namespace IPC
michael@0 169
michael@0 170 #endif // CHROME_COMMON_IPC_CHANNEL_POSIX_H_

mercurial