Line data Source code
1 : //
2 : // Copyright (c) 2023 Vinnie Falco (vinnie.falco@gmail.com)
3 : //
4 : // Distributed under the Boost Software License, Version 1.0. (See accompanying
5 : // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6 : //
7 : // Official repository: https://github.com/cppalliance/buffers
8 : //
9 :
10 : #ifndef BOOST_BUFFERS_BUFFER_COPY_HPP
11 : #define BOOST_BUFFERS_BUFFER_COPY_HPP
12 :
13 : #include <boost/buffers/detail/config.hpp>
14 : #include <boost/buffers/range.hpp>
15 : #include <boost/buffers/type_traits.hpp>
16 : #include <boost/assert.hpp>
17 : #include <cstring>
18 : #include <utility>
19 :
20 : namespace boost {
21 : namespace buffers {
22 : namespace detail {
23 :
24 : struct buffer_copy_impl
25 : {
26 : template<
27 : class MutableBuffers,
28 : class ConstBuffers>
29 : std::size_t
30 601351 : operator()(
31 : MutableBuffers const& to,
32 : ConstBuffers const& from,
33 : std::size_t at_most =
34 : std::size_t(-1)) const noexcept
35 : {
36 : // If you get a compile error here it
37 : // means that one or both of your types
38 : // do not meet the requirements.
39 : static_assert(
40 : is_mutable_buffer_sequence<
41 : MutableBuffers>::value,
42 : "Type requirements not met");
43 : static_assert(
44 : is_const_buffer_sequence<
45 : ConstBuffers>::value,
46 : "Type requirements not met");
47 :
48 601351 : std::size_t total = 0;
49 601351 : std::size_t pos0 = 0;
50 601351 : std::size_t pos1 = 0;
51 601351 : auto const end0 = end(from);
52 601351 : auto const end1 = end(to);
53 601351 : auto it0 = begin(from);
54 601351 : auto it1 = begin(to);
55 601351 : while(
56 1421704 : total < at_most &&
57 2723364 : it0 != end0 &&
58 : it1 != end1)
59 : {
60 : const_buffer b0 =
61 826815 : const_buffer(*it0) + pos0;
62 : mutable_buffer b1 =
63 826815 : mutable_buffer(*it1) + pos1;
64 : std::size_t const amount =
65 4114737 : [&]
66 : {
67 826815 : std::size_t n = b0.size();
68 826815 : if( n > b1.size())
69 23316 : n = b1.size();
70 826815 : if( n > at_most - total)
71 4878 : n = at_most - total;
72 826815 : if(n != 0)
73 803049 : std::memcpy(
74 : b1.data(),
75 : b0.data(),
76 : n);
77 826815 : return n;
78 826815 : }();
79 826815 : total += amount;
80 826815 : if(amount == b1.size())
81 : {
82 592314 : ++it1;
83 592314 : pos1 = 0;
84 : }
85 : else
86 : {
87 234501 : pos1 += amount;
88 : }
89 826815 : if(amount == b0.size())
90 : {
91 800037 : ++it0;
92 800037 : pos0 = 0;
93 : }
94 : else
95 : {
96 26778 : pos0 += amount;
97 : }
98 : }
99 601351 : return total;
100 : }
101 : };
102 :
103 : } // detail
104 :
105 : /** Copy buffer contents
106 : */
107 : constexpr detail::buffer_copy_impl buffer_copy{};
108 :
109 : } // buffers
110 : } // boost
111 :
112 : #endif
|