basic_serial_port.hpp 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695
  1. //
  2. // basic_serial_port.hpp
  3. // ~~~~~~~~~~~~~~~~~~~~~
  4. //
  5. // Copyright (c) 2003-2015 Christopher M. Kohlhoff (chris at kohlhoff dot com)
  6. // Copyright (c) 2008 Rep Invariant Systems, Inc. ([email protected])
  7. //
  8. // Distributed under the Boost Software License, Version 1.0. (See accompanying
  9. // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  10. //
  11. #ifndef ASIO_BASIC_SERIAL_PORT_HPP
  12. #define ASIO_BASIC_SERIAL_PORT_HPP
  13. #if defined(_MSC_VER) && (_MSC_VER >= 1200)
  14. # pragma once
  15. #endif // defined(_MSC_VER) && (_MSC_VER >= 1200)
  16. #include "asio/detail/config.hpp"
  17. #if defined(ASIO_HAS_SERIAL_PORT) \
  18. || defined(GENERATING_DOCUMENTATION)
  19. #include <string>
  20. #include "asio/basic_io_object.hpp"
  21. #include "asio/detail/handler_type_requirements.hpp"
  22. #include "asio/detail/throw_error.hpp"
  23. #include "asio/error.hpp"
  24. #include "asio/serial_port_base.hpp"
  25. #include "asio/serial_port_service.hpp"
  26. #include "asio/detail/push_options.hpp"
  27. namespace asio {
  28. /// Provides serial port functionality.
  29. /**
  30. * The basic_serial_port class template provides functionality that is common
  31. * to all serial ports.
  32. *
  33. * @par Thread Safety
  34. * @e Distinct @e objects: Safe.@n
  35. * @e Shared @e objects: Unsafe.
  36. */
  37. template <typename SerialPortService = serial_port_service>
  38. class basic_serial_port
  39. : public basic_io_object<SerialPortService>,
  40. public serial_port_base
  41. {
  42. public:
  43. /// (Deprecated: Use native_handle_type.) The native representation of a
  44. /// serial port.
  45. typedef typename SerialPortService::native_handle_type native_type;
  46. /// The native representation of a serial port.
  47. typedef typename SerialPortService::native_handle_type native_handle_type;
  48. /// A basic_serial_port is always the lowest layer.
  49. typedef basic_serial_port<SerialPortService> lowest_layer_type;
  50. /// Construct a basic_serial_port without opening it.
  51. /**
  52. * This constructor creates a serial port without opening it.
  53. *
  54. * @param io_service The io_service object that the serial port will use to
  55. * dispatch handlers for any asynchronous operations performed on the port.
  56. */
  57. explicit basic_serial_port(asio::io_service& io_service)
  58. : basic_io_object<SerialPortService>(io_service)
  59. {
  60. }
  61. /// Construct and open a basic_serial_port.
  62. /**
  63. * This constructor creates and opens a serial port for the specified device
  64. * name.
  65. *
  66. * @param io_service The io_service object that the serial port will use to
  67. * dispatch handlers for any asynchronous operations performed on the port.
  68. *
  69. * @param device The platform-specific device name for this serial
  70. * port.
  71. */
  72. explicit basic_serial_port(asio::io_service& io_service,
  73. const char* device)
  74. : basic_io_object<SerialPortService>(io_service)
  75. {
  76. asio::error_code ec;
  77. this->get_service().open(this->get_implementation(), device, ec);
  78. asio::detail::throw_error(ec, "open");
  79. }
  80. /// Construct and open a basic_serial_port.
  81. /**
  82. * This constructor creates and opens a serial port for the specified device
  83. * name.
  84. *
  85. * @param io_service The io_service object that the serial port will use to
  86. * dispatch handlers for any asynchronous operations performed on the port.
  87. *
  88. * @param device The platform-specific device name for this serial
  89. * port.
  90. */
  91. explicit basic_serial_port(asio::io_service& io_service,
  92. const std::string& device)
  93. : basic_io_object<SerialPortService>(io_service)
  94. {
  95. asio::error_code ec;
  96. this->get_service().open(this->get_implementation(), device, ec);
  97. asio::detail::throw_error(ec, "open");
  98. }
  99. /// Construct a basic_serial_port on an existing native serial port.
  100. /**
  101. * This constructor creates a serial port object to hold an existing native
  102. * serial port.
  103. *
  104. * @param io_service The io_service object that the serial port will use to
  105. * dispatch handlers for any asynchronous operations performed on the port.
  106. *
  107. * @param native_serial_port A native serial port.
  108. *
  109. * @throws asio::system_error Thrown on failure.
  110. */
  111. basic_serial_port(asio::io_service& io_service,
  112. const native_handle_type& native_serial_port)
  113. : basic_io_object<SerialPortService>(io_service)
  114. {
  115. asio::error_code ec;
  116. this->get_service().assign(this->get_implementation(),
  117. native_serial_port, ec);
  118. asio::detail::throw_error(ec, "assign");
  119. }
  120. #if defined(ASIO_HAS_MOVE) || defined(GENERATING_DOCUMENTATION)
  121. /// Move-construct a basic_serial_port from another.
  122. /**
  123. * This constructor moves a serial port from one object to another.
  124. *
  125. * @param other The other basic_serial_port object from which the move will
  126. * occur.
  127. *
  128. * @note Following the move, the moved-from object is in the same state as if
  129. * constructed using the @c basic_serial_port(io_service&) constructor.
  130. */
  131. basic_serial_port(basic_serial_port&& other)
  132. : basic_io_object<SerialPortService>(
  133. ASIO_MOVE_CAST(basic_serial_port)(other))
  134. {
  135. }
  136. /// Move-assign a basic_serial_port from another.
  137. /**
  138. * This assignment operator moves a serial port from one object to another.
  139. *
  140. * @param other The other basic_serial_port object from which the move will
  141. * occur.
  142. *
  143. * @note Following the move, the moved-from object is in the same state as if
  144. * constructed using the @c basic_serial_port(io_service&) constructor.
  145. */
  146. basic_serial_port& operator=(basic_serial_port&& other)
  147. {
  148. basic_io_object<SerialPortService>::operator=(
  149. ASIO_MOVE_CAST(basic_serial_port)(other));
  150. return *this;
  151. }
  152. #endif // defined(ASIO_HAS_MOVE) || defined(GENERATING_DOCUMENTATION)
  153. /// Get a reference to the lowest layer.
  154. /**
  155. * This function returns a reference to the lowest layer in a stack of
  156. * layers. Since a basic_serial_port cannot contain any further layers, it
  157. * simply returns a reference to itself.
  158. *
  159. * @return A reference to the lowest layer in the stack of layers. Ownership
  160. * is not transferred to the caller.
  161. */
  162. lowest_layer_type& lowest_layer()
  163. {
  164. return *this;
  165. }
  166. /// Get a const reference to the lowest layer.
  167. /**
  168. * This function returns a const reference to the lowest layer in a stack of
  169. * layers. Since a basic_serial_port cannot contain any further layers, it
  170. * simply returns a reference to itself.
  171. *
  172. * @return A const reference to the lowest layer in the stack of layers.
  173. * Ownership is not transferred to the caller.
  174. */
  175. const lowest_layer_type& lowest_layer() const
  176. {
  177. return *this;
  178. }
  179. /// Open the serial port using the specified device name.
  180. /**
  181. * This function opens the serial port for the specified device name.
  182. *
  183. * @param device The platform-specific device name.
  184. *
  185. * @throws asio::system_error Thrown on failure.
  186. */
  187. void open(const std::string& device)
  188. {
  189. asio::error_code ec;
  190. this->get_service().open(this->get_implementation(), device, ec);
  191. asio::detail::throw_error(ec, "open");
  192. }
  193. /// Open the serial port using the specified device name.
  194. /**
  195. * This function opens the serial port using the given platform-specific
  196. * device name.
  197. *
  198. * @param device The platform-specific device name.
  199. *
  200. * @param ec Set the indicate what error occurred, if any.
  201. */
  202. asio::error_code open(const std::string& device,
  203. asio::error_code& ec)
  204. {
  205. return this->get_service().open(this->get_implementation(), device, ec);
  206. }
  207. /// Assign an existing native serial port to the serial port.
  208. /*
  209. * This function opens the serial port to hold an existing native serial port.
  210. *
  211. * @param native_serial_port A native serial port.
  212. *
  213. * @throws asio::system_error Thrown on failure.
  214. */
  215. void assign(const native_handle_type& native_serial_port)
  216. {
  217. asio::error_code ec;
  218. this->get_service().assign(this->get_implementation(),
  219. native_serial_port, ec);
  220. asio::detail::throw_error(ec, "assign");
  221. }
  222. /// Assign an existing native serial port to the serial port.
  223. /*
  224. * This function opens the serial port to hold an existing native serial port.
  225. *
  226. * @param native_serial_port A native serial port.
  227. *
  228. * @param ec Set to indicate what error occurred, if any.
  229. */
  230. asio::error_code assign(const native_handle_type& native_serial_port,
  231. asio::error_code& ec)
  232. {
  233. return this->get_service().assign(this->get_implementation(),
  234. native_serial_port, ec);
  235. }
  236. /// Determine whether the serial port is open.
  237. bool is_open() const
  238. {
  239. return this->get_service().is_open(this->get_implementation());
  240. }
  241. /// Close the serial port.
  242. /**
  243. * This function is used to close the serial port. Any asynchronous read or
  244. * write operations will be cancelled immediately, and will complete with the
  245. * asio::error::operation_aborted error.
  246. *
  247. * @throws asio::system_error Thrown on failure.
  248. */
  249. void close()
  250. {
  251. asio::error_code ec;
  252. this->get_service().close(this->get_implementation(), ec);
  253. asio::detail::throw_error(ec, "close");
  254. }
  255. /// Close the serial port.
  256. /**
  257. * This function is used to close the serial port. Any asynchronous read or
  258. * write operations will be cancelled immediately, and will complete with the
  259. * asio::error::operation_aborted error.
  260. *
  261. * @param ec Set to indicate what error occurred, if any.
  262. */
  263. asio::error_code close(asio::error_code& ec)
  264. {
  265. return this->get_service().close(this->get_implementation(), ec);
  266. }
  267. /// (Deprecated: Use native_handle().) Get the native serial port
  268. /// representation.
  269. /**
  270. * This function may be used to obtain the underlying representation of the
  271. * serial port. This is intended to allow access to native serial port
  272. * functionality that is not otherwise provided.
  273. */
  274. native_type native()
  275. {
  276. return this->get_service().native_handle(this->get_implementation());
  277. }
  278. /// Get the native serial port representation.
  279. /**
  280. * This function may be used to obtain the underlying representation of the
  281. * serial port. This is intended to allow access to native serial port
  282. * functionality that is not otherwise provided.
  283. */
  284. native_handle_type native_handle()
  285. {
  286. return this->get_service().native_handle(this->get_implementation());
  287. }
  288. /// Cancel all asynchronous operations associated with the serial port.
  289. /**
  290. * This function causes all outstanding asynchronous read or write operations
  291. * to finish immediately, and the handlers for cancelled operations will be
  292. * passed the asio::error::operation_aborted error.
  293. *
  294. * @throws asio::system_error Thrown on failure.
  295. */
  296. void cancel()
  297. {
  298. asio::error_code ec;
  299. this->get_service().cancel(this->get_implementation(), ec);
  300. asio::detail::throw_error(ec, "cancel");
  301. }
  302. /// Cancel all asynchronous operations associated with the serial port.
  303. /**
  304. * This function causes all outstanding asynchronous read or write operations
  305. * to finish immediately, and the handlers for cancelled operations will be
  306. * passed the asio::error::operation_aborted error.
  307. *
  308. * @param ec Set to indicate what error occurred, if any.
  309. */
  310. asio::error_code cancel(asio::error_code& ec)
  311. {
  312. return this->get_service().cancel(this->get_implementation(), ec);
  313. }
  314. /// Send a break sequence to the serial port.
  315. /**
  316. * This function causes a break sequence of platform-specific duration to be
  317. * sent out the serial port.
  318. *
  319. * @throws asio::system_error Thrown on failure.
  320. */
  321. void send_break()
  322. {
  323. asio::error_code ec;
  324. this->get_service().send_break(this->get_implementation(), ec);
  325. asio::detail::throw_error(ec, "send_break");
  326. }
  327. /// Send a break sequence to the serial port.
  328. /**
  329. * This function causes a break sequence of platform-specific duration to be
  330. * sent out the serial port.
  331. *
  332. * @param ec Set to indicate what error occurred, if any.
  333. */
  334. asio::error_code send_break(asio::error_code& ec)
  335. {
  336. return this->get_service().send_break(this->get_implementation(), ec);
  337. }
  338. /// Set an option on the serial port.
  339. /**
  340. * This function is used to set an option on the serial port.
  341. *
  342. * @param option The option value to be set on the serial port.
  343. *
  344. * @throws asio::system_error Thrown on failure.
  345. *
  346. * @sa SettableSerialPortOption @n
  347. * asio::serial_port_base::baud_rate @n
  348. * asio::serial_port_base::flow_control @n
  349. * asio::serial_port_base::parity @n
  350. * asio::serial_port_base::stop_bits @n
  351. * asio::serial_port_base::character_size
  352. */
  353. template <typename SettableSerialPortOption>
  354. void set_option(const SettableSerialPortOption& option)
  355. {
  356. asio::error_code ec;
  357. this->get_service().set_option(this->get_implementation(), option, ec);
  358. asio::detail::throw_error(ec, "set_option");
  359. }
  360. /// Set an option on the serial port.
  361. /**
  362. * This function is used to set an option on the serial port.
  363. *
  364. * @param option The option value to be set on the serial port.
  365. *
  366. * @param ec Set to indicate what error occurred, if any.
  367. *
  368. * @sa SettableSerialPortOption @n
  369. * asio::serial_port_base::baud_rate @n
  370. * asio::serial_port_base::flow_control @n
  371. * asio::serial_port_base::parity @n
  372. * asio::serial_port_base::stop_bits @n
  373. * asio::serial_port_base::character_size
  374. */
  375. template <typename SettableSerialPortOption>
  376. asio::error_code set_option(const SettableSerialPortOption& option,
  377. asio::error_code& ec)
  378. {
  379. return this->get_service().set_option(
  380. this->get_implementation(), option, ec);
  381. }
  382. /// Get an option from the serial port.
  383. /**
  384. * This function is used to get the current value of an option on the serial
  385. * port.
  386. *
  387. * @param option The option value to be obtained from the serial port.
  388. *
  389. * @throws asio::system_error Thrown on failure.
  390. *
  391. * @sa GettableSerialPortOption @n
  392. * asio::serial_port_base::baud_rate @n
  393. * asio::serial_port_base::flow_control @n
  394. * asio::serial_port_base::parity @n
  395. * asio::serial_port_base::stop_bits @n
  396. * asio::serial_port_base::character_size
  397. */
  398. template <typename GettableSerialPortOption>
  399. void get_option(GettableSerialPortOption& option)
  400. {
  401. asio::error_code ec;
  402. this->get_service().get_option(this->get_implementation(), option, ec);
  403. asio::detail::throw_error(ec, "get_option");
  404. }
  405. /// Get an option from the serial port.
  406. /**
  407. * This function is used to get the current value of an option on the serial
  408. * port.
  409. *
  410. * @param option The option value to be obtained from the serial port.
  411. *
  412. * @param ec Set to indicate what error occured, if any.
  413. *
  414. * @sa GettableSerialPortOption @n
  415. * asio::serial_port_base::baud_rate @n
  416. * asio::serial_port_base::flow_control @n
  417. * asio::serial_port_base::parity @n
  418. * asio::serial_port_base::stop_bits @n
  419. * asio::serial_port_base::character_size
  420. */
  421. template <typename GettableSerialPortOption>
  422. asio::error_code get_option(GettableSerialPortOption& option,
  423. asio::error_code& ec)
  424. {
  425. return this->get_service().get_option(
  426. this->get_implementation(), option, ec);
  427. }
  428. /// Write some data to the serial port.
  429. /**
  430. * This function is used to write data to the serial port. The function call
  431. * will block until one or more bytes of the data has been written
  432. * successfully, or until an error occurs.
  433. *
  434. * @param buffers One or more data buffers to be written to the serial port.
  435. *
  436. * @returns The number of bytes written.
  437. *
  438. * @throws asio::system_error Thrown on failure. An error code of
  439. * asio::error::eof indicates that the connection was closed by the
  440. * peer.
  441. *
  442. * @note The write_some operation may not transmit all of the data to the
  443. * peer. Consider using the @ref write function if you need to ensure that
  444. * all data is written before the blocking operation completes.
  445. *
  446. * @par Example
  447. * To write a single data buffer use the @ref buffer function as follows:
  448. * @code
  449. * serial_port.write_some(asio::buffer(data, size));
  450. * @endcode
  451. * See the @ref buffer documentation for information on writing multiple
  452. * buffers in one go, and how to use it with arrays, boost::array or
  453. * std::vector.
  454. */
  455. template <typename ConstBufferSequence>
  456. std::size_t write_some(const ConstBufferSequence& buffers)
  457. {
  458. asio::error_code ec;
  459. std::size_t s = this->get_service().write_some(
  460. this->get_implementation(), buffers, ec);
  461. asio::detail::throw_error(ec, "write_some");
  462. return s;
  463. }
  464. /// Write some data to the serial port.
  465. /**
  466. * This function is used to write data to the serial port. The function call
  467. * will block until one or more bytes of the data has been written
  468. * successfully, or until an error occurs.
  469. *
  470. * @param buffers One or more data buffers to be written to the serial port.
  471. *
  472. * @param ec Set to indicate what error occurred, if any.
  473. *
  474. * @returns The number of bytes written. Returns 0 if an error occurred.
  475. *
  476. * @note The write_some operation may not transmit all of the data to the
  477. * peer. Consider using the @ref write function if you need to ensure that
  478. * all data is written before the blocking operation completes.
  479. */
  480. template <typename ConstBufferSequence>
  481. std::size_t write_some(const ConstBufferSequence& buffers,
  482. asio::error_code& ec)
  483. {
  484. return this->get_service().write_some(
  485. this->get_implementation(), buffers, ec);
  486. }
  487. /// Start an asynchronous write.
  488. /**
  489. * This function is used to asynchronously write data to the serial port.
  490. * The function call always returns immediately.
  491. *
  492. * @param buffers One or more data buffers to be written to the serial port.
  493. * Although the buffers object may be copied as necessary, ownership of the
  494. * underlying memory blocks is retained by the caller, which must guarantee
  495. * that they remain valid until the handler is called.
  496. *
  497. * @param handler The handler to be called when the write operation completes.
  498. * Copies will be made of the handler as required. The function signature of
  499. * the handler must be:
  500. * @code void handler(
  501. * const asio::error_code& error, // Result of operation.
  502. * std::size_t bytes_transferred // Number of bytes written.
  503. * ); @endcode
  504. * Regardless of whether the asynchronous operation completes immediately or
  505. * not, the handler will not be invoked from within this function. Invocation
  506. * of the handler will be performed in a manner equivalent to using
  507. * asio::io_service::post().
  508. *
  509. * @note The write operation may not transmit all of the data to the peer.
  510. * Consider using the @ref async_write function if you need to ensure that all
  511. * data is written before the asynchronous operation completes.
  512. *
  513. * @par Example
  514. * To write a single data buffer use the @ref buffer function as follows:
  515. * @code
  516. * serial_port.async_write_some(asio::buffer(data, size), handler);
  517. * @endcode
  518. * See the @ref buffer documentation for information on writing multiple
  519. * buffers in one go, and how to use it with arrays, boost::array or
  520. * std::vector.
  521. */
  522. template <typename ConstBufferSequence, typename WriteHandler>
  523. ASIO_INITFN_RESULT_TYPE(WriteHandler,
  524. void (asio::error_code, std::size_t))
  525. async_write_some(const ConstBufferSequence& buffers,
  526. ASIO_MOVE_ARG(WriteHandler) handler)
  527. {
  528. // If you get an error on the following line it means that your handler does
  529. // not meet the documented type requirements for a WriteHandler.
  530. ASIO_WRITE_HANDLER_CHECK(WriteHandler, handler) type_check;
  531. return this->get_service().async_write_some(this->get_implementation(),
  532. buffers, ASIO_MOVE_CAST(WriteHandler)(handler));
  533. }
  534. /// Read some data from the serial port.
  535. /**
  536. * This function is used to read data from the serial port. The function
  537. * call will block until one or more bytes of data has been read successfully,
  538. * or until an error occurs.
  539. *
  540. * @param buffers One or more buffers into which the data will be read.
  541. *
  542. * @returns The number of bytes read.
  543. *
  544. * @throws asio::system_error Thrown on failure. An error code of
  545. * asio::error::eof indicates that the connection was closed by the
  546. * peer.
  547. *
  548. * @note The read_some operation may not read all of the requested number of
  549. * bytes. Consider using the @ref read function if you need to ensure that
  550. * the requested amount of data is read before the blocking operation
  551. * completes.
  552. *
  553. * @par Example
  554. * To read into a single data buffer use the @ref buffer function as follows:
  555. * @code
  556. * serial_port.read_some(asio::buffer(data, size));
  557. * @endcode
  558. * See the @ref buffer documentation for information on reading into multiple
  559. * buffers in one go, and how to use it with arrays, boost::array or
  560. * std::vector.
  561. */
  562. template <typename MutableBufferSequence>
  563. std::size_t read_some(const MutableBufferSequence& buffers)
  564. {
  565. asio::error_code ec;
  566. std::size_t s = this->get_service().read_some(
  567. this->get_implementation(), buffers, ec);
  568. asio::detail::throw_error(ec, "read_some");
  569. return s;
  570. }
  571. /// Read some data from the serial port.
  572. /**
  573. * This function is used to read data from the serial port. The function
  574. * call will block until one or more bytes of data has been read successfully,
  575. * or until an error occurs.
  576. *
  577. * @param buffers One or more buffers into which the data will be read.
  578. *
  579. * @param ec Set to indicate what error occurred, if any.
  580. *
  581. * @returns The number of bytes read. Returns 0 if an error occurred.
  582. *
  583. * @note The read_some operation may not read all of the requested number of
  584. * bytes. Consider using the @ref read function if you need to ensure that
  585. * the requested amount of data is read before the blocking operation
  586. * completes.
  587. */
  588. template <typename MutableBufferSequence>
  589. std::size_t read_some(const MutableBufferSequence& buffers,
  590. asio::error_code& ec)
  591. {
  592. return this->get_service().read_some(
  593. this->get_implementation(), buffers, ec);
  594. }
  595. /// Start an asynchronous read.
  596. /**
  597. * This function is used to asynchronously read data from the serial port.
  598. * The function call always returns immediately.
  599. *
  600. * @param buffers One or more buffers into which the data will be read.
  601. * Although the buffers object may be copied as necessary, ownership of the
  602. * underlying memory blocks is retained by the caller, which must guarantee
  603. * that they remain valid until the handler is called.
  604. *
  605. * @param handler The handler to be called when the read operation completes.
  606. * Copies will be made of the handler as required. The function signature of
  607. * the handler must be:
  608. * @code void handler(
  609. * const asio::error_code& error, // Result of operation.
  610. * std::size_t bytes_transferred // Number of bytes read.
  611. * ); @endcode
  612. * Regardless of whether the asynchronous operation completes immediately or
  613. * not, the handler will not be invoked from within this function. Invocation
  614. * of the handler will be performed in a manner equivalent to using
  615. * asio::io_service::post().
  616. *
  617. * @note The read operation may not read all of the requested number of bytes.
  618. * Consider using the @ref async_read function if you need to ensure that the
  619. * requested amount of data is read before the asynchronous operation
  620. * completes.
  621. *
  622. * @par Example
  623. * To read into a single data buffer use the @ref buffer function as follows:
  624. * @code
  625. * serial_port.async_read_some(asio::buffer(data, size), handler);
  626. * @endcode
  627. * See the @ref buffer documentation for information on reading into multiple
  628. * buffers in one go, and how to use it with arrays, boost::array or
  629. * std::vector.
  630. */
  631. template <typename MutableBufferSequence, typename ReadHandler>
  632. ASIO_INITFN_RESULT_TYPE(ReadHandler,
  633. void (asio::error_code, std::size_t))
  634. async_read_some(const MutableBufferSequence& buffers,
  635. ASIO_MOVE_ARG(ReadHandler) handler)
  636. {
  637. // If you get an error on the following line it means that your handler does
  638. // not meet the documented type requirements for a ReadHandler.
  639. ASIO_READ_HANDLER_CHECK(ReadHandler, handler) type_check;
  640. return this->get_service().async_read_some(this->get_implementation(),
  641. buffers, ASIO_MOVE_CAST(ReadHandler)(handler));
  642. }
  643. };
  644. } // namespace asio
  645. #include "asio/detail/pop_options.hpp"
  646. #endif // defined(ASIO_HAS_SERIAL_PORT)
  647. // || defined(GENERATING_DOCUMENTATION)
  648. #endif // ASIO_BASIC_SERIAL_PORT_HPP