Statistics
| Revision:

root / tmp / org.txm.statsengine.r.core.win32 / res / win32 / library / BH / include / boost / asio / basic_socket.hpp @ 2486

History | View | Annotate | Download (51.6 kB)

1
//
2
// basic_socket.hpp
3
// ~~~~~~~~~~~~~~~~
4
//
5
// Copyright (c) 2003-2015 Christopher M. Kohlhoff (chris at kohlhoff dot com)
6
//
7
// Distributed under the Boost Software License, Version 1.0. (See accompanying
8
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
9
//
10

    
11
#ifndef BOOST_ASIO_BASIC_SOCKET_HPP
12
#define BOOST_ASIO_BASIC_SOCKET_HPP
13

    
14
#if defined(_MSC_VER) && (_MSC_VER >= 1200)
15
# pragma once
16
#endif // defined(_MSC_VER) && (_MSC_VER >= 1200)
17

    
18
#include <boost/asio/detail/config.hpp>
19
#include <boost/asio/async_result.hpp>
20
#include <boost/asio/basic_io_object.hpp>
21
#include <boost/asio/detail/handler_type_requirements.hpp>
22
#include <boost/asio/detail/throw_error.hpp>
23
#include <boost/asio/detail/type_traits.hpp>
24
#include <boost/asio/error.hpp>
25
#include <boost/asio/socket_base.hpp>
26

    
27
#include <boost/asio/detail/push_options.hpp>
28

    
29
namespace boost {
30
namespace asio {
31

    
32
/// Provides socket functionality.
33
/**
34
 * The basic_socket class template provides functionality that is common to both
35
 * stream-oriented and datagram-oriented sockets.
36
 *
37
 * @par Thread Safety
38
 * @e Distinct @e objects: Safe.@n
39
 * @e Shared @e objects: Unsafe.
40
 */
41
template <typename Protocol, typename SocketService>
42
class basic_socket
43
  : public basic_io_object<SocketService>,
44
    public socket_base
45
{
46
public:
47
  /// (Deprecated: Use native_handle_type.) The native representation of a
48
  /// socket.
49
  typedef typename SocketService::native_handle_type native_type;
50

    
51
  /// The native representation of a socket.
52
  typedef typename SocketService::native_handle_type native_handle_type;
53

    
54
  /// The protocol type.
55
  typedef Protocol protocol_type;
56

    
57
  /// The endpoint type.
58
  typedef typename Protocol::endpoint endpoint_type;
59

    
60
  /// A basic_socket is always the lowest layer.
61
  typedef basic_socket<Protocol, SocketService> lowest_layer_type;
62

    
63
  /// Construct a basic_socket without opening it.
64
  /**
65
   * This constructor creates a socket without opening it.
66
   *
67
   * @param io_service The io_service object that the socket will use to
68
   * dispatch handlers for any asynchronous operations performed on the socket.
69
   */
70
  explicit basic_socket(boost::asio::io_service& io_service)
71
    : basic_io_object<SocketService>(io_service)
72
  {
73
  }
74

    
75
  /// Construct and open a basic_socket.
76
  /**
77
   * This constructor creates and opens a socket.
78
   *
79
   * @param io_service The io_service object that the socket will use to
80
   * dispatch handlers for any asynchronous operations performed on the socket.
81
   *
82
   * @param protocol An object specifying protocol parameters to be used.
83
   *
84
   * @throws boost::system::system_error Thrown on failure.
85
   */
86
  basic_socket(boost::asio::io_service& io_service,
87
      const protocol_type& protocol)
88
    : basic_io_object<SocketService>(io_service)
89
  {
90
    boost::system::error_code ec;
91
    this->get_service().open(this->get_implementation(), protocol, ec);
92
    boost::asio::detail::throw_error(ec, "open");
93
  }
94

    
95
  /// Construct a basic_socket, opening it and binding it to the given local
96
  /// endpoint.
97
  /**
98
   * This constructor creates a socket and automatically opens it bound to the
99
   * specified endpoint on the local machine. The protocol used is the protocol
100
   * associated with the given endpoint.
101
   *
102
   * @param io_service The io_service object that the socket will use to
103
   * dispatch handlers for any asynchronous operations performed on the socket.
104
   *
105
   * @param endpoint An endpoint on the local machine to which the socket will
106
   * be bound.
107
   *
108
   * @throws boost::system::system_error Thrown on failure.
109
   */
110
  basic_socket(boost::asio::io_service& io_service,
111
      const endpoint_type& endpoint)
112
    : basic_io_object<SocketService>(io_service)
113
  {
114
    boost::system::error_code ec;
115
    const protocol_type protocol = endpoint.protocol();
116
    this->get_service().open(this->get_implementation(), protocol, ec);
117
    boost::asio::detail::throw_error(ec, "open");
118
    this->get_service().bind(this->get_implementation(), endpoint, ec);
119
    boost::asio::detail::throw_error(ec, "bind");
120
  }
121

    
122
  /// Construct a basic_socket on an existing native socket.
123
  /**
124
   * This constructor creates a socket object to hold an existing native socket.
125
   *
126
   * @param io_service The io_service object that the socket will use to
127
   * dispatch handlers for any asynchronous operations performed on the socket.
128
   *
129
   * @param protocol An object specifying protocol parameters to be used.
130
   *
131
   * @param native_socket A native socket.
132
   *
133
   * @throws boost::system::system_error Thrown on failure.
134
   */
135
  basic_socket(boost::asio::io_service& io_service,
136
      const protocol_type& protocol, const native_handle_type& native_socket)
137
    : basic_io_object<SocketService>(io_service)
138
  {
139
    boost::system::error_code ec;
140
    this->get_service().assign(this->get_implementation(),
141
        protocol, native_socket, ec);
142
    boost::asio::detail::throw_error(ec, "assign");
143
  }
144

    
145
#if defined(BOOST_ASIO_HAS_MOVE) || defined(GENERATING_DOCUMENTATION)
146
  /// Move-construct a basic_socket from another.
147
  /**
148
   * This constructor moves a socket from one object to another.
149
   *
150
   * @param other The other basic_socket object from which the move will
151
   * occur.
152
   *
153
   * @note Following the move, the moved-from object is in the same state as if
154
   * constructed using the @c basic_socket(io_service&) constructor.
155
   */
156
  basic_socket(basic_socket&& other)
157
    : basic_io_object<SocketService>(
158
        BOOST_ASIO_MOVE_CAST(basic_socket)(other))
159
  {
160
  }
161

    
162
  /// Move-assign a basic_socket from another.
163
  /**
164
   * This assignment operator moves a socket from one object to another.
165
   *
166
   * @param other The other basic_socket object from which the move will
167
   * occur.
168
   *
169
   * @note Following the move, the moved-from object is in the same state as if
170
   * constructed using the @c basic_socket(io_service&) constructor.
171
   */
172
  basic_socket& operator=(basic_socket&& other)
173
  {
174
    basic_io_object<SocketService>::operator=(
175
        BOOST_ASIO_MOVE_CAST(basic_socket)(other));
176
    return *this;
177
  }
178

    
179
  // All sockets have access to each other's implementations.
180
  template <typename Protocol1, typename SocketService1>
181
  friend class basic_socket;
182

    
183
  /// Move-construct a basic_socket from a socket of another protocol type.
184
  /**
185
   * This constructor moves a socket from one object to another.
186
   *
187
   * @param other The other basic_socket object from which the move will
188
   * occur.
189
   *
190
   * @note Following the move, the moved-from object is in the same state as if
191
   * constructed using the @c basic_socket(io_service&) constructor.
192
   */
193
  template <typename Protocol1, typename SocketService1>
194
  basic_socket(basic_socket<Protocol1, SocketService1>&& other,
195
      typename enable_if<is_convertible<Protocol1, Protocol>::value>::type* = 0)
196
    : basic_io_object<SocketService>(other.get_io_service())
197
  {
198
    this->get_service().template converting_move_construct<Protocol1>(
199
        this->get_implementation(), other.get_implementation());
200
  }
201

    
202
  /// Move-assign a basic_socket from a socket of another protocol type.
203
  /**
204
   * This assignment operator moves a socket from one object to another.
205
   *
206
   * @param other The other basic_socket object from which the move will
207
   * occur.
208
   *
209
   * @note Following the move, the moved-from object is in the same state as if
210
   * constructed using the @c basic_socket(io_service&) constructor.
211
   */
212
  template <typename Protocol1, typename SocketService1>
213
  typename enable_if<is_convertible<Protocol1, Protocol>::value,
214
      basic_socket>::type& operator=(
215
        basic_socket<Protocol1, SocketService1>&& other)
216
  {
217
    basic_socket tmp(BOOST_ASIO_MOVE_CAST2(basic_socket<
218
            Protocol1, SocketService1>)(other));
219
    basic_io_object<SocketService>::operator=(
220
        BOOST_ASIO_MOVE_CAST(basic_socket)(tmp));
221
    return *this;
222
  }
223
#endif // defined(BOOST_ASIO_HAS_MOVE) || defined(GENERATING_DOCUMENTATION)
224

    
225
  /// Get a reference to the lowest layer.
226
  /**
227
   * This function returns a reference to the lowest layer in a stack of
228
   * layers. Since a basic_socket cannot contain any further layers, it simply
229
   * returns a reference to itself.
230
   *
231
   * @return A reference to the lowest layer in the stack of layers. Ownership
232
   * is not transferred to the caller.
233
   */
234
  lowest_layer_type& lowest_layer()
235
  {
236
    return *this;
237
  }
238

    
239
  /// Get a const reference to the lowest layer.
240
  /**
241
   * This function returns a const reference to the lowest layer in a stack of
242
   * layers. Since a basic_socket cannot contain any further layers, it simply
243
   * returns a reference to itself.
244
   *
245
   * @return A const reference to the lowest layer in the stack of layers.
246
   * Ownership is not transferred to the caller.
247
   */
248
  const lowest_layer_type& lowest_layer() const
249
  {
250
    return *this;
251
  }
252

    
253
  /// Open the socket using the specified protocol.
254
  /**
255
   * This function opens the socket so that it will use the specified protocol.
256
   *
257
   * @param protocol An object specifying protocol parameters to be used.
258
   *
259
   * @throws boost::system::system_error Thrown on failure.
260
   *
261
   * @par Example
262
   * @code
263
   * boost::asio::ip::tcp::socket socket(io_service);
264
   * socket.open(boost::asio::ip::tcp::v4());
265
   * @endcode
266
   */
267
  void open(const protocol_type& protocol = protocol_type())
268
  {
269
    boost::system::error_code ec;
270
    this->get_service().open(this->get_implementation(), protocol, ec);
271
    boost::asio::detail::throw_error(ec, "open");
272
  }
273

    
274
  /// Open the socket using the specified protocol.
275
  /**
276
   * This function opens the socket so that it will use the specified protocol.
277
   *
278
   * @param protocol An object specifying which protocol is to be used.
279
   *
280
   * @param ec Set to indicate what error occurred, if any.
281
   *
282
   * @par Example
283
   * @code
284
   * boost::asio::ip::tcp::socket socket(io_service);
285
   * boost::system::error_code ec;
286
   * socket.open(boost::asio::ip::tcp::v4(), ec);
287
   * if (ec)
288
   * {
289
   *   // An error occurred.
290
   * }
291
   * @endcode
292
   */
293
  boost::system::error_code open(const protocol_type& protocol,
294
      boost::system::error_code& ec)
295
  {
296
    return this->get_service().open(this->get_implementation(), protocol, ec);
297
  }
298

    
299
  /// Assign an existing native socket to the socket.
300
  /*
301
   * This function opens the socket to hold an existing native socket.
302
   *
303
   * @param protocol An object specifying which protocol is to be used.
304
   *
305
   * @param native_socket A native socket.
306
   *
307
   * @throws boost::system::system_error Thrown on failure.
308
   */
309
  void assign(const protocol_type& protocol,
310
      const native_handle_type& native_socket)
311
  {
312
    boost::system::error_code ec;
313
    this->get_service().assign(this->get_implementation(),
314
        protocol, native_socket, ec);
315
    boost::asio::detail::throw_error(ec, "assign");
316
  }
317

    
318
  /// Assign an existing native socket to the socket.
319
  /*
320
   * This function opens the socket to hold an existing native socket.
321
   *
322
   * @param protocol An object specifying which protocol is to be used.
323
   *
324
   * @param native_socket A native socket.
325
   *
326
   * @param ec Set to indicate what error occurred, if any.
327
   */
328
  boost::system::error_code assign(const protocol_type& protocol,
329
      const native_handle_type& native_socket, boost::system::error_code& ec)
330
  {
331
    return this->get_service().assign(this->get_implementation(),
332
        protocol, native_socket, ec);
333
  }
334

    
335
  /// Determine whether the socket is open.
336
  bool is_open() const
337
  {
338
    return this->get_service().is_open(this->get_implementation());
339
  }
340

    
341
  /// Close the socket.
342
  /**
343
   * This function is used to close the socket. Any asynchronous send, receive
344
   * or connect operations will be cancelled immediately, and will complete
345
   * with the boost::asio::error::operation_aborted error.
346
   *
347
   * @throws boost::system::system_error Thrown on failure. Note that, even if
348
   * the function indicates an error, the underlying descriptor is closed.
349
   *
350
   * @note For portable behaviour with respect to graceful closure of a
351
   * connected socket, call shutdown() before closing the socket.
352
   */
353
  void close()
354
  {
355
    boost::system::error_code ec;
356
    this->get_service().close(this->get_implementation(), ec);
357
    boost::asio::detail::throw_error(ec, "close");
358
  }
359

    
360
  /// Close the socket.
361
  /**
362
   * This function is used to close the socket. Any asynchronous send, receive
363
   * or connect operations will be cancelled immediately, and will complete
364
   * with the boost::asio::error::operation_aborted error.
365
   *
366
   * @param ec Set to indicate what error occurred, if any. Note that, even if
367
   * the function indicates an error, the underlying descriptor is closed.
368
   *
369
   * @par Example
370
   * @code
371
   * boost::asio::ip::tcp::socket socket(io_service);
372
   * ...
373
   * boost::system::error_code ec;
374
   * socket.close(ec);
375
   * if (ec)
376
   * {
377
   *   // An error occurred.
378
   * }
379
   * @endcode
380
   *
381
   * @note For portable behaviour with respect to graceful closure of a
382
   * connected socket, call shutdown() before closing the socket.
383
   */
384
  boost::system::error_code close(boost::system::error_code& ec)
385
  {
386
    return this->get_service().close(this->get_implementation(), ec);
387
  }
388

    
389
  /// (Deprecated: Use native_handle().) Get the native socket representation.
390
  /**
391
   * This function may be used to obtain the underlying representation of the
392
   * socket. This is intended to allow access to native socket functionality
393
   * that is not otherwise provided.
394
   */
395
  native_type native()
396
  {
397
    return this->get_service().native_handle(this->get_implementation());
398
  }
399

    
400
  /// Get the native socket representation.
401
  /**
402
   * This function may be used to obtain the underlying representation of the
403
   * socket. This is intended to allow access to native socket functionality
404
   * that is not otherwise provided.
405
   */
406
  native_handle_type native_handle()
407
  {
408
    return this->get_service().native_handle(this->get_implementation());
409
  }
410

    
411
  /// Cancel all asynchronous operations associated with the socket.
412
  /**
413
   * This function causes all outstanding asynchronous connect, send and receive
414
   * operations to finish immediately, and the handlers for cancelled operations
415
   * will be passed the boost::asio::error::operation_aborted error.
416
   *
417
   * @throws boost::system::system_error Thrown on failure.
418
   *
419
   * @note Calls to cancel() will always fail with
420
   * boost::asio::error::operation_not_supported when run on Windows XP, Windows
421
   * Server 2003, and earlier versions of Windows, unless
422
   * BOOST_ASIO_ENABLE_CANCELIO is defined. However, the CancelIo function has
423
   * two issues that should be considered before enabling its use:
424
   *
425
   * @li It will only cancel asynchronous operations that were initiated in the
426
   * current thread.
427
   *
428
   * @li It can appear to complete without error, but the request to cancel the
429
   * unfinished operations may be silently ignored by the operating system.
430
   * Whether it works or not seems to depend on the drivers that are installed.
431
   *
432
   * For portable cancellation, consider using one of the following
433
   * alternatives:
434
   *
435
   * @li Disable asio's I/O completion port backend by defining
436
   * BOOST_ASIO_DISABLE_IOCP.
437
   *
438
   * @li Use the close() function to simultaneously cancel the outstanding
439
   * operations and close the socket.
440
   *
441
   * When running on Windows Vista, Windows Server 2008, and later, the
442
   * CancelIoEx function is always used. This function does not have the
443
   * problems described above.
444
   */
445
#if defined(BOOST_ASIO_MSVC) && (BOOST_ASIO_MSVC >= 1400) \
446
  && (!defined(_WIN32_WINNT) || _WIN32_WINNT < 0x0600) \
447
  && !defined(BOOST_ASIO_ENABLE_CANCELIO)
448
  __declspec(deprecated("By default, this function always fails with "
449
        "operation_not_supported when used on Windows XP, Windows Server 2003, "
450
        "or earlier. Consult documentation for details."))
451
#endif
452
  void cancel()
453
  {
454
    boost::system::error_code ec;
455
    this->get_service().cancel(this->get_implementation(), ec);
456
    boost::asio::detail::throw_error(ec, "cancel");
457
  }
458

    
459
  /// Cancel all asynchronous operations associated with the socket.
460
  /**
461
   * This function causes all outstanding asynchronous connect, send and receive
462
   * operations to finish immediately, and the handlers for cancelled operations
463
   * will be passed the boost::asio::error::operation_aborted error.
464
   *
465
   * @param ec Set to indicate what error occurred, if any.
466
   *
467
   * @note Calls to cancel() will always fail with
468
   * boost::asio::error::operation_not_supported when run on Windows XP, Windows
469
   * Server 2003, and earlier versions of Windows, unless
470
   * BOOST_ASIO_ENABLE_CANCELIO is defined. However, the CancelIo function has
471
   * two issues that should be considered before enabling its use:
472
   *
473
   * @li It will only cancel asynchronous operations that were initiated in the
474
   * current thread.
475
   *
476
   * @li It can appear to complete without error, but the request to cancel the
477
   * unfinished operations may be silently ignored by the operating system.
478
   * Whether it works or not seems to depend on the drivers that are installed.
479
   *
480
   * For portable cancellation, consider using one of the following
481
   * alternatives:
482
   *
483
   * @li Disable asio's I/O completion port backend by defining
484
   * BOOST_ASIO_DISABLE_IOCP.
485
   *
486
   * @li Use the close() function to simultaneously cancel the outstanding
487
   * operations and close the socket.
488
   *
489
   * When running on Windows Vista, Windows Server 2008, and later, the
490
   * CancelIoEx function is always used. This function does not have the
491
   * problems described above.
492
   */
493
#if defined(BOOST_ASIO_MSVC) && (BOOST_ASIO_MSVC >= 1400) \
494
  && (!defined(_WIN32_WINNT) || _WIN32_WINNT < 0x0600) \
495
  && !defined(BOOST_ASIO_ENABLE_CANCELIO)
496
  __declspec(deprecated("By default, this function always fails with "
497
        "operation_not_supported when used on Windows XP, Windows Server 2003, "
498
        "or earlier. Consult documentation for details."))
499
#endif
500
  boost::system::error_code cancel(boost::system::error_code& ec)
501
  {
502
    return this->get_service().cancel(this->get_implementation(), ec);
503
  }
504

    
505
  /// Determine whether the socket is at the out-of-band data mark.
506
  /**
507
   * This function is used to check whether the socket input is currently
508
   * positioned at the out-of-band data mark.
509
   *
510
   * @return A bool indicating whether the socket is at the out-of-band data
511
   * mark.
512
   *
513
   * @throws boost::system::system_error Thrown on failure.
514
   */
515
  bool at_mark() const
516
  {
517
    boost::system::error_code ec;
518
    bool b = this->get_service().at_mark(this->get_implementation(), ec);
519
    boost::asio::detail::throw_error(ec, "at_mark");
520
    return b;
521
  }
522

    
523
  /// Determine whether the socket is at the out-of-band data mark.
524
  /**
525
   * This function is used to check whether the socket input is currently
526
   * positioned at the out-of-band data mark.
527
   *
528
   * @param ec Set to indicate what error occurred, if any.
529
   *
530
   * @return A bool indicating whether the socket is at the out-of-band data
531
   * mark.
532
   */
533
  bool at_mark(boost::system::error_code& ec) const
534
  {
535
    return this->get_service().at_mark(this->get_implementation(), ec);
536
  }
537

    
538
  /// Determine the number of bytes available for reading.
539
  /**
540
   * This function is used to determine the number of bytes that may be read
541
   * without blocking.
542
   *
543
   * @return The number of bytes that may be read without blocking, or 0 if an
544
   * error occurs.
545
   *
546
   * @throws boost::system::system_error Thrown on failure.
547
   */
548
  std::size_t available() const
549
  {
550
    boost::system::error_code ec;
551
    std::size_t s = this->get_service().available(
552
        this->get_implementation(), ec);
553
    boost::asio::detail::throw_error(ec, "available");
554
    return s;
555
  }
556

    
557
  /// Determine the number of bytes available for reading.
558
  /**
559
   * This function is used to determine the number of bytes that may be read
560
   * without blocking.
561
   *
562
   * @param ec Set to indicate what error occurred, if any.
563
   *
564
   * @return The number of bytes that may be read without blocking, or 0 if an
565
   * error occurs.
566
   */
567
  std::size_t available(boost::system::error_code& ec) const
568
  {
569
    return this->get_service().available(this->get_implementation(), ec);
570
  }
571

    
572
  /// Bind the socket to the given local endpoint.
573
  /**
574
   * This function binds the socket to the specified endpoint on the local
575
   * machine.
576
   *
577
   * @param endpoint An endpoint on the local machine to which the socket will
578
   * be bound.
579
   *
580
   * @throws boost::system::system_error Thrown on failure.
581
   *
582
   * @par Example
583
   * @code
584
   * boost::asio::ip::tcp::socket socket(io_service);
585
   * socket.open(boost::asio::ip::tcp::v4());
586
   * socket.bind(boost::asio::ip::tcp::endpoint(
587
   *       boost::asio::ip::tcp::v4(), 12345));
588
   * @endcode
589
   */
590
  void bind(const endpoint_type& endpoint)
591
  {
592
    boost::system::error_code ec;
593
    this->get_service().bind(this->get_implementation(), endpoint, ec);
594
    boost::asio::detail::throw_error(ec, "bind");
595
  }
596

    
597
  /// Bind the socket to the given local endpoint.
598
  /**
599
   * This function binds the socket to the specified endpoint on the local
600
   * machine.
601
   *
602
   * @param endpoint An endpoint on the local machine to which the socket will
603
   * be bound.
604
   *
605
   * @param ec Set to indicate what error occurred, if any.
606
   *
607
   * @par Example
608
   * @code
609
   * boost::asio::ip::tcp::socket socket(io_service);
610
   * socket.open(boost::asio::ip::tcp::v4());
611
   * boost::system::error_code ec;
612
   * socket.bind(boost::asio::ip::tcp::endpoint(
613
   *       boost::asio::ip::tcp::v4(), 12345), ec);
614
   * if (ec)
615
   * {
616
   *   // An error occurred.
617
   * }
618
   * @endcode
619
   */
620
  boost::system::error_code bind(const endpoint_type& endpoint,
621
      boost::system::error_code& ec)
622
  {
623
    return this->get_service().bind(this->get_implementation(), endpoint, ec);
624
  }
625

    
626
  /// Connect the socket to the specified endpoint.
627
  /**
628
   * This function is used to connect a socket to the specified remote endpoint.
629
   * The function call will block until the connection is successfully made or
630
   * an error occurs.
631
   *
632
   * The socket is automatically opened if it is not already open. If the
633
   * connect fails, and the socket was automatically opened, the socket is
634
   * not returned to the closed state.
635
   *
636
   * @param peer_endpoint The remote endpoint to which the socket will be
637
   * connected.
638
   *
639
   * @throws boost::system::system_error Thrown on failure.
640
   *
641
   * @par Example
642
   * @code
643
   * boost::asio::ip::tcp::socket socket(io_service);
644
   * boost::asio::ip::tcp::endpoint endpoint(
645
   *     boost::asio::ip::address::from_string("1.2.3.4"), 12345);
646
   * socket.connect(endpoint);
647
   * @endcode
648
   */
649
  void connect(const endpoint_type& peer_endpoint)
650
  {
651
    boost::system::error_code ec;
652
    if (!is_open())
653
    {
654
      this->get_service().open(this->get_implementation(),
655
          peer_endpoint.protocol(), ec);
656
      boost::asio::detail::throw_error(ec, "connect");
657
    }
658
    this->get_service().connect(this->get_implementation(), peer_endpoint, ec);
659
    boost::asio::detail::throw_error(ec, "connect");
660
  }
661

    
662
  /// Connect the socket to the specified endpoint.
663
  /**
664
   * This function is used to connect a socket to the specified remote endpoint.
665
   * The function call will block until the connection is successfully made or
666
   * an error occurs.
667
   *
668
   * The socket is automatically opened if it is not already open. If the
669
   * connect fails, and the socket was automatically opened, the socket is
670
   * not returned to the closed state.
671
   *
672
   * @param peer_endpoint The remote endpoint to which the socket will be
673
   * connected.
674
   *
675
   * @param ec Set to indicate what error occurred, if any.
676
   *
677
   * @par Example
678
   * @code
679
   * boost::asio::ip::tcp::socket socket(io_service);
680
   * boost::asio::ip::tcp::endpoint endpoint(
681
   *     boost::asio::ip::address::from_string("1.2.3.4"), 12345);
682
   * boost::system::error_code ec;
683
   * socket.connect(endpoint, ec);
684
   * if (ec)
685
   * {
686
   *   // An error occurred.
687
   * }
688
   * @endcode
689
   */
690
  boost::system::error_code connect(const endpoint_type& peer_endpoint,
691
      boost::system::error_code& ec)
692
  {
693
    if (!is_open())
694
    {
695
      if (this->get_service().open(this->get_implementation(),
696
            peer_endpoint.protocol(), ec))
697
      {
698
        return ec;
699
      }
700
    }
701

    
702
    return this->get_service().connect(
703
        this->get_implementation(), peer_endpoint, ec);
704
  }
705

    
706
  /// Start an asynchronous connect.
707
  /**
708
   * This function is used to asynchronously connect a socket to the specified
709
   * remote endpoint. The function call always returns immediately.
710
   *
711
   * The socket is automatically opened if it is not already open. If the
712
   * connect fails, and the socket was automatically opened, the socket is
713
   * not returned to the closed state.
714
   *
715
   * @param peer_endpoint The remote endpoint to which the socket will be
716
   * connected. Copies will be made of the endpoint object as required.
717
   *
718
   * @param handler The handler to be called when the connection operation
719
   * completes. Copies will be made of the handler as required. The function
720
   * signature of the handler must be:
721
   * @code void handler(
722
   *   const boost::system::error_code& error // Result of operation
723
   * ); @endcode
724
   * Regardless of whether the asynchronous operation completes immediately or
725
   * not, the handler will not be invoked from within this function. Invocation
726
   * of the handler will be performed in a manner equivalent to using
727
   * boost::asio::io_service::post().
728
   *
729
   * @par Example
730
   * @code
731
   * void connect_handler(const boost::system::error_code& error)
732
   * {
733
   *   if (!error)
734
   *   {
735
   *     // Connect succeeded.
736
   *   }
737
   * }
738
   *
739
   * ...
740
   *
741
   * boost::asio::ip::tcp::socket socket(io_service);
742
   * boost::asio::ip::tcp::endpoint endpoint(
743
   *     boost::asio::ip::address::from_string("1.2.3.4"), 12345);
744
   * socket.async_connect(endpoint, connect_handler);
745
   * @endcode
746
   */
747
  template <typename ConnectHandler>
748
  BOOST_ASIO_INITFN_RESULT_TYPE(ConnectHandler,
749
      void (boost::system::error_code))
750
  async_connect(const endpoint_type& peer_endpoint,
751
      BOOST_ASIO_MOVE_ARG(ConnectHandler) handler)
752
  {
753
    // If you get an error on the following line it means that your handler does
754
    // not meet the documented type requirements for a ConnectHandler.
755
    BOOST_ASIO_CONNECT_HANDLER_CHECK(ConnectHandler, handler) type_check;
756

    
757
    if (!is_open())
758
    {
759
      boost::system::error_code ec;
760
      const protocol_type protocol = peer_endpoint.protocol();
761
      if (this->get_service().open(this->get_implementation(), protocol, ec))
762
      {
763
        detail::async_result_init<
764
          ConnectHandler, void (boost::system::error_code)> init(
765
            BOOST_ASIO_MOVE_CAST(ConnectHandler)(handler));
766

    
767
        this->get_io_service().post(
768
            boost::asio::detail::bind_handler(
769
              BOOST_ASIO_MOVE_CAST(BOOST_ASIO_HANDLER_TYPE(
770
                ConnectHandler, void (boost::system::error_code)))(
771
                  init.handler), ec));
772

    
773
        return init.result.get();
774
      }
775
    }
776

    
777
    return this->get_service().async_connect(this->get_implementation(),
778
        peer_endpoint, BOOST_ASIO_MOVE_CAST(ConnectHandler)(handler));
779
  }
780

    
781
  /// Set an option on the socket.
782
  /**
783
   * This function is used to set an option on the socket.
784
   *
785
   * @param option The new option value to be set on the socket.
786
   *
787
   * @throws boost::system::system_error Thrown on failure.
788
   *
789
   * @sa SettableSocketOption @n
790
   * boost::asio::socket_base::broadcast @n
791
   * boost::asio::socket_base::do_not_route @n
792
   * boost::asio::socket_base::keep_alive @n
793
   * boost::asio::socket_base::linger @n
794
   * boost::asio::socket_base::receive_buffer_size @n
795
   * boost::asio::socket_base::receive_low_watermark @n
796
   * boost::asio::socket_base::reuse_address @n
797
   * boost::asio::socket_base::send_buffer_size @n
798
   * boost::asio::socket_base::send_low_watermark @n
799
   * boost::asio::ip::multicast::join_group @n
800
   * boost::asio::ip::multicast::leave_group @n
801
   * boost::asio::ip::multicast::enable_loopback @n
802
   * boost::asio::ip::multicast::outbound_interface @n
803
   * boost::asio::ip::multicast::hops @n
804
   * boost::asio::ip::tcp::no_delay
805
   *
806
   * @par Example
807
   * Setting the IPPROTO_TCP/TCP_NODELAY option:
808
   * @code
809
   * boost::asio::ip::tcp::socket socket(io_service);
810
   * ...
811
   * boost::asio::ip::tcp::no_delay option(true);
812
   * socket.set_option(option);
813
   * @endcode
814
   */
815
  template <typename SettableSocketOption>
816
  void set_option(const SettableSocketOption& option)
817
  {
818
    boost::system::error_code ec;
819
    this->get_service().set_option(this->get_implementation(), option, ec);
820
    boost::asio::detail::throw_error(ec, "set_option");
821
  }
822

    
823
  /// Set an option on the socket.
824
  /**
825
   * This function is used to set an option on the socket.
826
   *
827
   * @param option The new option value to be set on the socket.
828
   *
829
   * @param ec Set to indicate what error occurred, if any.
830
   *
831
   * @sa SettableSocketOption @n
832
   * boost::asio::socket_base::broadcast @n
833
   * boost::asio::socket_base::do_not_route @n
834
   * boost::asio::socket_base::keep_alive @n
835
   * boost::asio::socket_base::linger @n
836
   * boost::asio::socket_base::receive_buffer_size @n
837
   * boost::asio::socket_base::receive_low_watermark @n
838
   * boost::asio::socket_base::reuse_address @n
839
   * boost::asio::socket_base::send_buffer_size @n
840
   * boost::asio::socket_base::send_low_watermark @n
841
   * boost::asio::ip::multicast::join_group @n
842
   * boost::asio::ip::multicast::leave_group @n
843
   * boost::asio::ip::multicast::enable_loopback @n
844
   * boost::asio::ip::multicast::outbound_interface @n
845
   * boost::asio::ip::multicast::hops @n
846
   * boost::asio::ip::tcp::no_delay
847
   *
848
   * @par Example
849
   * Setting the IPPROTO_TCP/TCP_NODELAY option:
850
   * @code
851
   * boost::asio::ip::tcp::socket socket(io_service);
852
   * ...
853
   * boost::asio::ip::tcp::no_delay option(true);
854
   * boost::system::error_code ec;
855
   * socket.set_option(option, ec);
856
   * if (ec)
857
   * {
858
   *   // An error occurred.
859
   * }
860
   * @endcode
861
   */
862
  template <typename SettableSocketOption>
863
  boost::system::error_code set_option(const SettableSocketOption& option,
864
      boost::system::error_code& ec)
865
  {
866
    return this->get_service().set_option(
867
        this->get_implementation(), option, ec);
868
  }
869

    
870
  /// Get an option from the socket.
871
  /**
872
   * This function is used to get the current value of an option on the socket.
873
   *
874
   * @param option The option value to be obtained from the socket.
875
   *
876
   * @throws boost::system::system_error Thrown on failure.
877
   *
878
   * @sa GettableSocketOption @n
879
   * boost::asio::socket_base::broadcast @n
880
   * boost::asio::socket_base::do_not_route @n
881
   * boost::asio::socket_base::keep_alive @n
882
   * boost::asio::socket_base::linger @n
883
   * boost::asio::socket_base::receive_buffer_size @n
884
   * boost::asio::socket_base::receive_low_watermark @n
885
   * boost::asio::socket_base::reuse_address @n
886
   * boost::asio::socket_base::send_buffer_size @n
887
   * boost::asio::socket_base::send_low_watermark @n
888
   * boost::asio::ip::multicast::join_group @n
889
   * boost::asio::ip::multicast::leave_group @n
890
   * boost::asio::ip::multicast::enable_loopback @n
891
   * boost::asio::ip::multicast::outbound_interface @n
892
   * boost::asio::ip::multicast::hops @n
893
   * boost::asio::ip::tcp::no_delay
894
   *
895
   * @par Example
896
   * Getting the value of the SOL_SOCKET/SO_KEEPALIVE option:
897
   * @code
898
   * boost::asio::ip::tcp::socket socket(io_service);
899
   * ...
900
   * boost::asio::ip::tcp::socket::keep_alive option;
901
   * socket.get_option(option);
902
   * bool is_set = option.value();
903
   * @endcode
904
   */
905
  template <typename GettableSocketOption>
906
  void get_option(GettableSocketOption& option) const
907
  {
908
    boost::system::error_code ec;
909
    this->get_service().get_option(this->get_implementation(), option, ec);
910
    boost::asio::detail::throw_error(ec, "get_option");
911
  }
912

    
913
  /// Get an option from the socket.
914
  /**
915
   * This function is used to get the current value of an option on the socket.
916
   *
917
   * @param option The option value to be obtained from the socket.
918
   *
919
   * @param ec Set to indicate what error occurred, if any.
920
   *
921
   * @sa GettableSocketOption @n
922
   * boost::asio::socket_base::broadcast @n
923
   * boost::asio::socket_base::do_not_route @n
924
   * boost::asio::socket_base::keep_alive @n
925
   * boost::asio::socket_base::linger @n
926
   * boost::asio::socket_base::receive_buffer_size @n
927
   * boost::asio::socket_base::receive_low_watermark @n
928
   * boost::asio::socket_base::reuse_address @n
929
   * boost::asio::socket_base::send_buffer_size @n
930
   * boost::asio::socket_base::send_low_watermark @n
931
   * boost::asio::ip::multicast::join_group @n
932
   * boost::asio::ip::multicast::leave_group @n
933
   * boost::asio::ip::multicast::enable_loopback @n
934
   * boost::asio::ip::multicast::outbound_interface @n
935
   * boost::asio::ip::multicast::hops @n
936
   * boost::asio::ip::tcp::no_delay
937
   *
938
   * @par Example
939
   * Getting the value of the SOL_SOCKET/SO_KEEPALIVE option:
940
   * @code
941
   * boost::asio::ip::tcp::socket socket(io_service);
942
   * ...
943
   * boost::asio::ip::tcp::socket::keep_alive option;
944
   * boost::system::error_code ec;
945
   * socket.get_option(option, ec);
946
   * if (ec)
947
   * {
948
   *   // An error occurred.
949
   * }
950
   * bool is_set = option.value();
951
   * @endcode
952
   */
953
  template <typename GettableSocketOption>
954
  boost::system::error_code get_option(GettableSocketOption& option,
955
      boost::system::error_code& ec) const
956
  {
957
    return this->get_service().get_option(
958
        this->get_implementation(), option, ec);
959
  }
960

    
961
  /// Perform an IO control command on the socket.
962
  /**
963
   * This function is used to execute an IO control command on the socket.
964
   *
965
   * @param command The IO control command to be performed on the socket.
966
   *
967
   * @throws boost::system::system_error Thrown on failure.
968
   *
969
   * @sa IoControlCommand @n
970
   * boost::asio::socket_base::bytes_readable @n
971
   * boost::asio::socket_base::non_blocking_io
972
   *
973
   * @par Example
974
   * Getting the number of bytes ready to read:
975
   * @code
976
   * boost::asio::ip::tcp::socket socket(io_service);
977
   * ...
978
   * boost::asio::ip::tcp::socket::bytes_readable command;
979
   * socket.io_control(command);
980
   * std::size_t bytes_readable = command.get();
981
   * @endcode
982
   */
983
  template <typename IoControlCommand>
984
  void io_control(IoControlCommand& command)
985
  {
986
    boost::system::error_code ec;
987
    this->get_service().io_control(this->get_implementation(), command, ec);
988
    boost::asio::detail::throw_error(ec, "io_control");
989
  }
990

    
991
  /// Perform an IO control command on the socket.
992
  /**
993
   * This function is used to execute an IO control command on the socket.
994
   *
995
   * @param command The IO control command to be performed on the socket.
996
   *
997
   * @param ec Set to indicate what error occurred, if any.
998
   *
999
   * @sa IoControlCommand @n
1000
   * boost::asio::socket_base::bytes_readable @n
1001
   * boost::asio::socket_base::non_blocking_io
1002
   *
1003
   * @par Example
1004
   * Getting the number of bytes ready to read:
1005
   * @code
1006
   * boost::asio::ip::tcp::socket socket(io_service);
1007
   * ...
1008
   * boost::asio::ip::tcp::socket::bytes_readable command;
1009
   * boost::system::error_code ec;
1010
   * socket.io_control(command, ec);
1011
   * if (ec)
1012
   * {
1013
   *   // An error occurred.
1014
   * }
1015
   * std::size_t bytes_readable = command.get();
1016
   * @endcode
1017
   */
1018
  template <typename IoControlCommand>
1019
  boost::system::error_code io_control(IoControlCommand& command,
1020
      boost::system::error_code& ec)
1021
  {
1022
    return this->get_service().io_control(
1023
        this->get_implementation(), command, ec);
1024
  }
1025

    
1026
  /// Gets the non-blocking mode of the socket.
1027
  /**
1028
   * @returns @c true if the socket's synchronous operations will fail with
1029
   * boost::asio::error::would_block if they are unable to perform the requested
1030
   * operation immediately. If @c false, synchronous operations will block
1031
   * until complete.
1032
   *
1033
   * @note The non-blocking mode has no effect on the behaviour of asynchronous
1034
   * operations. Asynchronous operations will never fail with the error
1035
   * boost::asio::error::would_block.
1036
   */
1037
  bool non_blocking() const
1038
  {
1039
    return this->get_service().non_blocking(this->get_implementation());
1040
  }
1041

    
1042
  /// Sets the non-blocking mode of the socket.
1043
  /**
1044
   * @param mode If @c true, the socket's synchronous operations will fail with
1045
   * boost::asio::error::would_block if they are unable to perform the requested
1046
   * operation immediately. If @c false, synchronous operations will block
1047
   * until complete.
1048
   *
1049
   * @throws boost::system::system_error Thrown on failure.
1050
   *
1051
   * @note The non-blocking mode has no effect on the behaviour of asynchronous
1052
   * operations. Asynchronous operations will never fail with the error
1053
   * boost::asio::error::would_block.
1054
   */
1055
  void non_blocking(bool mode)
1056
  {
1057
    boost::system::error_code ec;
1058
    this->get_service().non_blocking(this->get_implementation(), mode, ec);
1059
    boost::asio::detail::throw_error(ec, "non_blocking");
1060
  }
1061

    
1062
  /// Sets the non-blocking mode of the socket.
1063
  /**
1064
   * @param mode If @c true, the socket's synchronous operations will fail with
1065
   * boost::asio::error::would_block if they are unable to perform the requested
1066
   * operation immediately. If @c false, synchronous operations will block
1067
   * until complete.
1068
   *
1069
   * @param ec Set to indicate what error occurred, if any.
1070
   *
1071
   * @note The non-blocking mode has no effect on the behaviour of asynchronous
1072
   * operations. Asynchronous operations will never fail with the error
1073
   * boost::asio::error::would_block.
1074
   */
1075
  boost::system::error_code non_blocking(
1076
      bool mode, boost::system::error_code& ec)
1077
  {
1078
    return this->get_service().non_blocking(
1079
        this->get_implementation(), mode, ec);
1080
  }
1081

    
1082
  /// Gets the non-blocking mode of the native socket implementation.
1083
  /**
1084
   * This function is used to retrieve the non-blocking mode of the underlying
1085
   * native socket. This mode has no effect on the behaviour of the socket
1086
   * object's synchronous operations.
1087
   *
1088
   * @returns @c true if the underlying socket is in non-blocking mode and
1089
   * direct system calls may fail with boost::asio::error::would_block (or the
1090
   * equivalent system error).
1091
   *
1092
   * @note The current non-blocking mode is cached by the socket object.
1093
   * Consequently, the return value may be incorrect if the non-blocking mode
1094
   * was set directly on the native socket.
1095
   *
1096
   * @par Example
1097
   * This function is intended to allow the encapsulation of arbitrary
1098
   * non-blocking system calls as asynchronous operations, in a way that is
1099
   * transparent to the user of the socket object. The following example
1100
   * illustrates how Linux's @c sendfile system call might be encapsulated:
1101
   * @code template <typename Handler>
1102
   * struct sendfile_op
1103
   * {
1104
   *   tcp::socket& sock_;
1105
   *   int fd_;
1106
   *   Handler handler_;
1107
   *   off_t offset_;
1108
   *   std::size_t total_bytes_transferred_;
1109
   *
1110
   *   // Function call operator meeting WriteHandler requirements.
1111
   *   // Used as the handler for the async_write_some operation.
1112
   *   void operator()(boost::system::error_code ec, std::size_t)
1113
   *   {
1114
   *     // Put the underlying socket into non-blocking mode.
1115
   *     if (!ec)
1116
   *       if (!sock_.native_non_blocking())
1117
   *         sock_.native_non_blocking(true, ec);
1118
   *
1119
   *     if (!ec)
1120
   *     {
1121
   *       for (;;)
1122
   *       {
1123
   *         // Try the system call.
1124
   *         errno = 0;
1125
   *         int n = ::sendfile(sock_.native_handle(), fd_, &offset_, 65536);
1126
   *         ec = boost::system::error_code(n < 0 ? errno : 0,
1127
   *             boost::asio::error::get_system_category());
1128
   *         total_bytes_transferred_ += ec ? 0 : n;
1129
   *
1130
   *         // Retry operation immediately if interrupted by signal.
1131
   *         if (ec == boost::asio::error::interrupted)
1132
   *           continue;
1133
   *
1134
   *         // Check if we need to run the operation again.
1135
   *         if (ec == boost::asio::error::would_block
1136
   *             || ec == boost::asio::error::try_again)
1137
   *         {
1138
   *           // We have to wait for the socket to become ready again.
1139
   *           sock_.async_write_some(boost::asio::null_buffers(), *this);
1140
   *           return;
1141
   *         }
1142
   *
1143
   *         if (ec || n == 0)
1144
   *         {
1145
   *           // An error occurred, or we have reached the end of the file.
1146
   *           // Either way we must exit the loop so we can call the handler.
1147
   *           break;
1148
   *         }
1149
   *
1150
   *         // Loop around to try calling sendfile again.
1151
   *       }
1152
   *     }
1153
   *
1154
   *     // Pass result back to user's handler.
1155
   *     handler_(ec, total_bytes_transferred_);
1156
   *   }
1157
   * };
1158
   *
1159
   * template <typename Handler>
1160
   * void async_sendfile(tcp::socket& sock, int fd, Handler h)
1161
   * {
1162
   *   sendfile_op<Handler> op = { sock, fd, h, 0, 0 };
1163
   *   sock.async_write_some(boost::asio::null_buffers(), op);
1164
   * } @endcode
1165
   */
1166
  bool native_non_blocking() const
1167
  {
1168
    return this->get_service().native_non_blocking(this->get_implementation());
1169
  }
1170

    
1171
  /// Sets the non-blocking mode of the native socket implementation.
1172
  /**
1173
   * This function is used to modify the non-blocking mode of the underlying
1174
   * native socket. It has no effect on the behaviour of the socket object's
1175
   * synchronous operations.
1176
   *
1177
   * @param mode If @c true, the underlying socket is put into non-blocking
1178
   * mode and direct system calls may fail with boost::asio::error::would_block
1179
   * (or the equivalent system error).
1180
   *
1181
   * @throws boost::system::system_error Thrown on failure. If the @c mode is
1182
   * @c false, but the current value of @c non_blocking() is @c true, this
1183
   * function fails with boost::asio::error::invalid_argument, as the
1184
   * combination does not make sense.
1185
   *
1186
   * @par Example
1187
   * This function is intended to allow the encapsulation of arbitrary
1188
   * non-blocking system calls as asynchronous operations, in a way that is
1189
   * transparent to the user of the socket object. The following example
1190
   * illustrates how Linux's @c sendfile system call might be encapsulated:
1191
   * @code template <typename Handler>
1192
   * struct sendfile_op
1193
   * {
1194
   *   tcp::socket& sock_;
1195
   *   int fd_;
1196
   *   Handler handler_;
1197
   *   off_t offset_;
1198
   *   std::size_t total_bytes_transferred_;
1199
   *
1200
   *   // Function call operator meeting WriteHandler requirements.
1201
   *   // Used as the handler for the async_write_some operation.
1202
   *   void operator()(boost::system::error_code ec, std::size_t)
1203
   *   {
1204
   *     // Put the underlying socket into non-blocking mode.
1205
   *     if (!ec)
1206
   *       if (!sock_.native_non_blocking())
1207
   *         sock_.native_non_blocking(true, ec);
1208
   *
1209
   *     if (!ec)
1210
   *     {
1211
   *       for (;;)
1212
   *       {
1213
   *         // Try the system call.
1214
   *         errno = 0;
1215
   *         int n = ::sendfile(sock_.native_handle(), fd_, &offset_, 65536);
1216
   *         ec = boost::system::error_code(n < 0 ? errno : 0,
1217
   *             boost::asio::error::get_system_category());
1218
   *         total_bytes_transferred_ += ec ? 0 : n;
1219
   *
1220
   *         // Retry operation immediately if interrupted by signal.
1221
   *         if (ec == boost::asio::error::interrupted)
1222
   *           continue;
1223
   *
1224
   *         // Check if we need to run the operation again.
1225
   *         if (ec == boost::asio::error::would_block
1226
   *             || ec == boost::asio::error::try_again)
1227
   *         {
1228
   *           // We have to wait for the socket to become ready again.
1229
   *           sock_.async_write_some(boost::asio::null_buffers(), *this);
1230
   *           return;
1231
   *         }
1232
   *
1233
   *         if (ec || n == 0)
1234
   *         {
1235
   *           // An error occurred, or we have reached the end of the file.
1236
   *           // Either way we must exit the loop so we can call the handler.
1237
   *           break;
1238
   *         }
1239
   *
1240
   *         // Loop around to try calling sendfile again.
1241
   *       }
1242
   *     }
1243
   *
1244
   *     // Pass result back to user's handler.
1245
   *     handler_(ec, total_bytes_transferred_);
1246
   *   }
1247
   * };
1248
   *
1249
   * template <typename Handler>
1250
   * void async_sendfile(tcp::socket& sock, int fd, Handler h)
1251
   * {
1252
   *   sendfile_op<Handler> op = { sock, fd, h, 0, 0 };
1253
   *   sock.async_write_some(boost::asio::null_buffers(), op);
1254
   * } @endcode
1255
   */
1256
  void native_non_blocking(bool mode)
1257
  {
1258
    boost::system::error_code ec;
1259
    this->get_service().native_non_blocking(
1260
        this->get_implementation(), mode, ec);
1261
    boost::asio::detail::throw_error(ec, "native_non_blocking");
1262
  }
1263

    
1264
  /// Sets the non-blocking mode of the native socket implementation.
1265
  /**
1266
   * This function is used to modify the non-blocking mode of the underlying
1267
   * native socket. It has no effect on the behaviour of the socket object's
1268
   * synchronous operations.
1269
   *
1270
   * @param mode If @c true, the underlying socket is put into non-blocking
1271
   * mode and direct system calls may fail with boost::asio::error::would_block
1272
   * (or the equivalent system error).
1273
   *
1274
   * @param ec Set to indicate what error occurred, if any. If the @c mode is
1275
   * @c false, but the current value of @c non_blocking() is @c true, this
1276
   * function fails with boost::asio::error::invalid_argument, as the
1277
   * combination does not make sense.
1278
   *
1279
   * @par Example
1280
   * This function is intended to allow the encapsulation of arbitrary
1281
   * non-blocking system calls as asynchronous operations, in a way that is
1282
   * transparent to the user of the socket object. The following example
1283
   * illustrates how Linux's @c sendfile system call might be encapsulated:
1284
   * @code template <typename Handler>
1285
   * struct sendfile_op
1286
   * {
1287
   *   tcp::socket& sock_;
1288
   *   int fd_;
1289
   *   Handler handler_;
1290
   *   off_t offset_;
1291
   *   std::size_t total_bytes_transferred_;
1292
   *
1293
   *   // Function call operator meeting WriteHandler requirements.
1294
   *   // Used as the handler for the async_write_some operation.
1295
   *   void operator()(boost::system::error_code ec, std::size_t)
1296
   *   {
1297
   *     // Put the underlying socket into non-blocking mode.
1298
   *     if (!ec)
1299
   *       if (!sock_.native_non_blocking())
1300
   *         sock_.native_non_blocking(true, ec);
1301
   *
1302
   *     if (!ec)
1303
   *     {
1304
   *       for (;;)
1305
   *       {
1306
   *         // Try the system call.
1307
   *         errno = 0;
1308
   *         int n = ::sendfile(sock_.native_handle(), fd_, &offset_, 65536);
1309
   *         ec = boost::system::error_code(n < 0 ? errno : 0,
1310
   *             boost::asio::error::get_system_category());
1311
   *         total_bytes_transferred_ += ec ? 0 : n;
1312
   *
1313
   *         // Retry operation immediately if interrupted by signal.
1314
   *         if (ec == boost::asio::error::interrupted)
1315
   *           continue;
1316
   *
1317
   *         // Check if we need to run the operation again.
1318
   *         if (ec == boost::asio::error::would_block
1319
   *             || ec == boost::asio::error::try_again)
1320
   *         {
1321
   *           // We have to wait for the socket to become ready again.
1322
   *           sock_.async_write_some(boost::asio::null_buffers(), *this);
1323
   *           return;
1324
   *         }
1325
   *
1326
   *         if (ec || n == 0)
1327
   *         {
1328
   *           // An error occurred, or we have reached the end of the file.
1329
   *           // Either way we must exit the loop so we can call the handler.
1330
   *           break;
1331
   *         }
1332
   *
1333
   *         // Loop around to try calling sendfile again.
1334
   *       }
1335
   *     }
1336
   *
1337
   *     // Pass result back to user's handler.
1338
   *     handler_(ec, total_bytes_transferred_);
1339
   *   }
1340
   * };
1341
   *
1342
   * template <typename Handler>
1343
   * void async_sendfile(tcp::socket& sock, int fd, Handler h)
1344
   * {
1345
   *   sendfile_op<Handler> op = { sock, fd, h, 0, 0 };
1346
   *   sock.async_write_some(boost::asio::null_buffers(), op);
1347
   * } @endcode
1348
   */
1349
  boost::system::error_code native_non_blocking(
1350
      bool mode, boost::system::error_code& ec)
1351
  {
1352
    return this->get_service().native_non_blocking(
1353
        this->get_implementation(), mode, ec);
1354
  }
1355

    
1356
  /// Get the local endpoint of the socket.
1357
  /**
1358
   * This function is used to obtain the locally bound endpoint of the socket.
1359
   *
1360
   * @returns An object that represents the local endpoint of the socket.
1361
   *
1362
   * @throws boost::system::system_error Thrown on failure.
1363
   *
1364
   * @par Example
1365
   * @code
1366
   * boost::asio::ip::tcp::socket socket(io_service);
1367
   * ...
1368
   * boost::asio::ip::tcp::endpoint endpoint = socket.local_endpoint();
1369
   * @endcode
1370
   */
1371
  endpoint_type local_endpoint() const
1372
  {
1373
    boost::system::error_code ec;
1374
    endpoint_type ep = this->get_service().local_endpoint(
1375
        this->get_implementation(), ec);
1376
    boost::asio::detail::throw_error(ec, "local_endpoint");
1377
    return ep;
1378
  }
1379

    
1380
  /// Get the local endpoint of the socket.
1381
  /**
1382
   * This function is used to obtain the locally bound endpoint of the socket.
1383
   *
1384
   * @param ec Set to indicate what error occurred, if any.
1385
   *
1386
   * @returns An object that represents the local endpoint of the socket.
1387
   * Returns a default-constructed endpoint object if an error occurred.
1388
   *
1389
   * @par Example
1390
   * @code
1391
   * boost::asio::ip::tcp::socket socket(io_service);
1392
   * ...
1393
   * boost::system::error_code ec;
1394
   * boost::asio::ip::tcp::endpoint endpoint = socket.local_endpoint(ec);
1395
   * if (ec)
1396
   * {
1397
   *   // An error occurred.
1398
   * }
1399
   * @endcode
1400
   */
1401
  endpoint_type local_endpoint(boost::system::error_code& ec) const
1402
  {
1403
    return this->get_service().local_endpoint(this->get_implementation(), ec);
1404
  }
1405

    
1406
  /// Get the remote endpoint of the socket.
1407
  /**
1408
   * This function is used to obtain the remote endpoint of the socket.
1409
   *
1410
   * @returns An object that represents the remote endpoint of the socket.
1411
   *
1412
   * @throws boost::system::system_error Thrown on failure.
1413
   *
1414
   * @par Example
1415
   * @code
1416
   * boost::asio::ip::tcp::socket socket(io_service);
1417
   * ...
1418
   * boost::asio::ip::tcp::endpoint endpoint = socket.remote_endpoint();
1419
   * @endcode
1420
   */
1421
  endpoint_type remote_endpoint() const
1422
  {
1423
    boost::system::error_code ec;
1424
    endpoint_type ep = this->get_service().remote_endpoint(
1425
        this->get_implementation(), ec);
1426
    boost::asio::detail::throw_error(ec, "remote_endpoint");
1427
    return ep;
1428
  }
1429

    
1430
  /// Get the remote endpoint of the socket.
1431
  /**
1432
   * This function is used to obtain the remote endpoint of the socket.
1433
   *
1434
   * @param ec Set to indicate what error occurred, if any.
1435
   *
1436
   * @returns An object that represents the remote endpoint of the socket.
1437
   * Returns a default-constructed endpoint object if an error occurred.
1438
   *
1439
   * @par Example
1440
   * @code
1441
   * boost::asio::ip::tcp::socket socket(io_service);
1442
   * ...
1443
   * boost::system::error_code ec;
1444
   * boost::asio::ip::tcp::endpoint endpoint = socket.remote_endpoint(ec);
1445
   * if (ec)
1446
   * {
1447
   *   // An error occurred.
1448
   * }
1449
   * @endcode
1450
   */
1451
  endpoint_type remote_endpoint(boost::system::error_code& ec) const
1452
  {
1453
    return this->get_service().remote_endpoint(this->get_implementation(), ec);
1454
  }
1455

    
1456
  /// Disable sends or receives on the socket.
1457
  /**
1458
   * This function is used to disable send operations, receive operations, or
1459
   * both.
1460
   *
1461
   * @param what Determines what types of operation will no longer be allowed.
1462
   *
1463
   * @throws boost::system::system_error Thrown on failure.
1464
   *
1465
   * @par Example
1466
   * Shutting down the send side of the socket:
1467
   * @code
1468
   * boost::asio::ip::tcp::socket socket(io_service);
1469
   * ...
1470
   * socket.shutdown(boost::asio::ip::tcp::socket::shutdown_send);
1471
   * @endcode
1472
   */
1473
  void shutdown(shutdown_type what)
1474
  {
1475
    boost::system::error_code ec;
1476
    this->get_service().shutdown(this->get_implementation(), what, ec);
1477
    boost::asio::detail::throw_error(ec, "shutdown");
1478
  }
1479

    
1480
  /// Disable sends or receives on the socket.
1481
  /**
1482
   * This function is used to disable send operations, receive operations, or
1483
   * both.
1484
   *
1485
   * @param what Determines what types of operation will no longer be allowed.
1486
   *
1487
   * @param ec Set to indicate what error occurred, if any.
1488
   *
1489
   * @par Example
1490
   * Shutting down the send side of the socket:
1491
   * @code
1492
   * boost::asio::ip::tcp::socket socket(io_service);
1493
   * ...
1494
   * boost::system::error_code ec;
1495
   * socket.shutdown(boost::asio::ip::tcp::socket::shutdown_send, ec);
1496
   * if (ec)
1497
   * {
1498
   *   // An error occurred.
1499
   * }
1500
   * @endcode
1501
   */
1502
  boost::system::error_code shutdown(shutdown_type what,
1503
      boost::system::error_code& ec)
1504
  {
1505
    return this->get_service().shutdown(this->get_implementation(), what, ec);
1506
  }
1507

    
1508
protected:
1509
  /// Protected destructor to prevent deletion through this type.
1510
  ~basic_socket()
1511
  {
1512
  }
1513
};
1514

    
1515
} // namespace asio
1516
} // namespace boost
1517

    
1518
#include <boost/asio/detail/pop_options.hpp>
1519

    
1520
#endif // BOOST_ASIO_BASIC_SOCKET_HPP