Apache Mesos
pid.hpp
Go to the documentation of this file.
1 // Licensed under the Apache License, Version 2.0 (the "License");
2 // you may not use this file except in compliance with the License.
3 // You may obtain a copy of the License at
4 //
5 // http://www.apache.org/licenses/LICENSE-2.0
6 //
7 // Unless required by applicable law or agreed to in writing, software
8 // distributed under the License is distributed on an "AS IS" BASIS,
9 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
10 // See the License for the specific language governing permissions and
11 // limitations under the License
12 
13 #ifndef __PROCESS_PID_HPP__
14 #define __PROCESS_PID_HPP__
15 
16 #include <stdint.h>
17 
18 #include <iosfwd>
19 #include <string>
20 
21 #include <boost/functional/hash.hpp>
22 
23 #include <process/address.hpp>
24 
25 #include <stout/ip.hpp>
26 
27 namespace process {
28 
29 // Forward declaration to break cyclic dependencies.
30 class ProcessBase;
31 
39 struct UPID
40 {
41  UPID() = default;
42 
43  UPID(const UPID& that) = default;
44 
45  UPID(UPID&& that) = default;
46 
47  UPID(const char* id_, const net::IP& ip_, uint16_t port_)
48  : id(id_), address(ip_, port_) { resolve(); }
49 
50  UPID(const char* id_, const network::inet::Address& address_)
51  : id(id_), address(address_) { resolve(); }
52 
53  UPID(const std::string& id_, const net::IP& ip_, uint16_t port_)
54  : id(id_), address(ip_, port_) { resolve(); }
55 
56  UPID(const std::string& id_, const network::inet::Address& address_)
57  : id(id_), address(address_) { resolve(); }
58 
59  /*implicit*/ UPID(const char* s);
60 
61  /*implicit*/ UPID(const std::string& s);
62 
63  /*implicit*/ UPID(const ProcessBase& process);
64 
65  UPID& operator=(const UPID& that) = default;
66 
67  UPID& operator=(UPID&& that) = default;
68 
69  operator std::string() const;
70 
71  operator bool() const
72  {
73  return id != "" && !address.ip.isAny() && address.port != 0;
74  }
75 
76  bool operator!() const // NOLINT(whitespace/operators)
77  {
78  return id == "" && address.ip.isAny() && address.port == 0;
79  }
80 
81  bool operator<(const UPID& that) const
82  {
83  if (address == that.address) {
84  return id < that.id;
85  } else {
86  return address < that.address;
87  }
88  }
89 
90  bool operator==(const UPID& that) const
91  {
92  return (id == that.id && address == that.address);
93  }
94 
95  bool operator!=(const UPID& that) const
96  {
97  return !(*this == that);
98  }
99 
100  // Attempts to resolve and cache a weak pointer to the ProcessBase
101  // to which this UPID refers.
102  void resolve();
103 
104  // TODO(benh): store all of the members of UPID behind a
105  // copy-on-write implementation because UPID is often copied but
106  // rarely written which means we could optimize performance by not
107  // making so many copies.
108 
109  // A copy-on-write string for performance.
110  //
111  // TODO(benh): Factor this out into a generic copy-on-write string.
112  struct ID
113  {
114  static const std::string EMPTY;
115 
116  ID() = default;
117 
118  ID(const std::string& s)
119  : id(std::make_shared<std::string>(s)) {}
120 
121  ID(std::string&& s)
122  : id(std::make_shared<std::string>(std::move(s))) {}
123 
124  ID& operator=(std::string&& that)
125  {
126  id = std::make_shared<std::string>(std::move(that));
127  return *this;
128  }
129 
130  bool operator==(const std::string& that) const
131  {
132  if (!id) {
133  return EMPTY == that;
134  }
135  return *id == that;
136  }
137 
138  bool operator==(const char* that) const
139  {
140  if (!id) {
141  return EMPTY == that;
142  }
143  return *id == that;
144  }
145 
146  bool operator!=(const std::string& that) const
147  {
148  return !(*this == that);
149  }
150 
151  bool operator<(const std::string& that) const
152  {
153  if (!id) {
154  return EMPTY < that;
155  }
156  return *id < that;
157  }
158 
159  operator const std::string&() const
160  {
161  if (!id) {
162  return EMPTY;
163  }
164  return *id;
165  }
166 
167  private:
168  std::shared_ptr<std::string> id;
169  } id;
170 
171  // TODO(asridharan): Ideally, the following `address` field should be of
172  // type `network::Address` so that the default address of the PID
173  // could be a unix domain socket or an IPv4/v6 address. This change
174  // however is disruptive at this point and should be done after we have
175  // introduced support for unix domain and IPv6 sockets into
176  // `libprocess`.
178 
179  // TODO(asridharan): Currently we are introducing only an `Optional`
180  // IPv6 address in the following `addresses` structure. This will
181  // help us initiate some basic IPv6 support for the
182  // `DockerContainerizer`. However, going forward, once we start
183  // supporting unix domain sockets and IPv4/IPv6 socket in
184  // `libprocess` we will add the following fields to this structure.
185  //
186  // Option<network::unix::Address> unix;
187  // Option<network::inet4::Address> v4;
188  //
189  // With the introduction of the above fields `libprocess` PID will
190  // be able to support unix, IPv4 and IPv6 sockets simultaneously.
191  struct
192  {
194  } addresses = {None()};
195 
196 protected:
197  friend class ProcessBase;
198  friend class ProcessManager;
199 
200  // A weak pointer to the actual process used to optimize enqueuing
201  // events without having to go through a shared lock in the
202  // `ProcessManager`. This is `None` if someone creates a UPID and
203  // doesn't call `resolve()` or if `resolve()` doesn't find a valid
204  // process (i.e., the process hasn't started or has terminated).
206 };
207 
208 
209 inline std::ostream& operator<<(std::ostream& stream, const UPID::ID& id)
210 {
211  const std::string& s = id;
212  return stream << s;
213 }
214 
215 
216 inline bool operator==(const std::string& s, const UPID::ID& id)
217 {
218  return id == s;
219 }
220 
221 
222 inline bool operator!=(const std::string& s, const UPID::ID& id)
223 {
224  return !(s == id);
225 }
226 
227 
228 inline std::string operator+(const UPID::ID& id, const std::string& s)
229 {
230  return (const std::string&) id + s;
231 }
232 
233 
234 inline std::string operator+(const UPID::ID& id, std::string&& s)
235 {
236  return (const std::string&) id + std::move(s);
237 }
238 
239 
240 inline std::string operator+(const std::string& s, const UPID::ID& id)
241 {
242  return s + (const std::string&) id;
243 }
244 
245 
246 inline std::string operator+(std::string&& s, const UPID::ID& id)
247 {
248  return std::move(s) + (const std::string&) id;
249 }
250 
251 
278 template <typename T = ProcessBase>
279 struct PID : UPID
280 {
281  // Need to declare PID<U> as a friend in order to write `reference`.
282  template <typename U>
283  friend struct PID;
284 
285  PID() : UPID() {}
286 
287  /*implicit*/ PID(const T* t) : UPID(static_cast<const ProcessBase&>(*t)) {}
288  /*implicit*/ PID(const T& t) : UPID(static_cast<const ProcessBase&>(t)) {}
289 
290  template <typename Base>
291  operator PID<Base>() const
292  {
293  // Only allow upcasts!
294  T* t = nullptr;
295  Base* base = t;
296  (void)base; // Eliminate unused base warning.
297  PID<Base> pid;
298  pid.id = id;
299  pid.address = address;
300  pid.addresses = addresses;
301  pid.reference = reference;
302  return pid;
303  }
304 };
305 
306 
307 // Outputing UPIDs and generating UPIDs using streams.
308 std::ostream& operator<<(std::ostream&, const UPID&);
309 std::istream& operator>>(std::istream&, UPID&);
310 
311 } // namespace process {
312 
313 namespace std {
314 
315 template <>
316 struct hash<process::UPID>
317 {
318  typedef size_t result_type;
319 
321 
322  result_type operator()(const argument_type& upid) const
323  {
324  size_t seed = 0;
325  boost::hash_combine(seed, (const std::string&) upid.id);
326  boost::hash_combine(seed, std::hash<net::IP>()(upid.address.ip));
327  boost::hash_combine(seed, upid.address.port);
328  return seed;
329  }
330 };
331 
332 } // namespace std {
333 
334 #endif // __PROCESS_PID_HPP__
static Address ANY_ANY()
Definition: address.hpp:157
ID & operator=(std::string &&that)
Definition: pid.hpp:124
std::ostream & operator<<(std::ostream &stream, const Future< T > &future)
Definition: future.hpp:1829
UPID & operator=(const UPID &that)=default
PID(const T &t)
Definition: pid.hpp:288
ID(std::string &&s)
Definition: pid.hpp:121
bool operator!=(const UPID &that) const
Definition: pid.hpp:95
network::inet::Address address
Definition: pid.hpp:177
Definition: pid.hpp:112
static const std::string EMPTY
Definition: pid.hpp:114
ID(const std::string &s)
Definition: pid.hpp:118
Definition: ip.hpp:682
bool isAny() const
Definition: ip.hpp:157
Definition: uuid.hpp:33
Definition: type_utils.hpp:510
Definition: process.hpp:72
bool operator<(const std::string &that) const
Definition: pid.hpp:151
event_base * base
UPID(const char *id_, const net::IP &ip_, uint16_t port_)
Definition: pid.hpp:47
struct process::UPID::@5 addresses
UPID(const char *id_, const network::inet::Address &address_)
Definition: pid.hpp:50
Definition: ip.hpp:73
bool operator<(const UPID &that) const
Definition: pid.hpp:81
bool operator!=(const std::string &that) const
Definition: pid.hpp:146
An "untyped" PID, used to encapsulate the process ID for lower-layer abstractions (eg...
Definition: pid.hpp:39
result_type operator()(const argument_type &upid) const
Definition: pid.hpp:322
Option< network::inet6::Address > v6
Definition: pid.hpp:193
bool operator==(const UPID &that) const
Definition: pid.hpp:90
uint16_t port
Definition: address.hpp:134
Option< std::weak_ptr< ProcessBase * > > reference
Definition: pid.hpp:205
Definition: address.hpp:51
std::string operator+(const UPID::ID &id, const std::string &s)
Definition: pid.hpp:228
friend class ProcessManager
Definition: pid.hpp:198
A "process identifier" used to uniquely identify a process when dispatching messages.
Definition: pid.hpp:279
Definition: none.hpp:27
Definition: executor.hpp:48
bool operator!() const
Definition: pid.hpp:76
UPID(const std::string &id_, const network::inet::Address &address_)
Definition: pid.hpp:56
PID(const T *t)
Definition: pid.hpp:287
bool operator==(const std::string &that) const
Definition: pid.hpp:130
bool operator==(const char *that) const
Definition: pid.hpp:138
UPID()=default
UPID(const std::string &id_, const net::IP &ip_, uint16_t port_)
Definition: pid.hpp:53
struct process::UPID::ID id
std::istream & operator>>(std::istream &, UPID &)
net::IP ip
Definition: address.hpp:133
process::UPID argument_type
Definition: pid.hpp:320
PID()
Definition: pid.hpp:285
size_t result_type
Definition: pid.hpp:318