1 +
//
 
2 +
// Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com)
 
3 +
// Copyright (c) 2022 Alan de Freitas (alandefreitas@gmail.com)
 
4 +
//
 
5 +
// Distributed under the Boost Software License, Version 1.0. (See accompanying
 
6 +
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
 
7 +
//
 
8 +
// Official repository: https://github.com/boostorg/url
 
9 +
//
 
10 +

 
11 +
#ifndef BOOST_URL_IMPL_URL_HPP
 
12 +
#define BOOST_URL_IMPL_URL_HPP
 
13 +

 
14 +
#include <boost/url/detail/except.hpp>
 
15 +
#include <boost/assert.hpp>
 
16 +
#include <cstring>
 
17 +

 
18 +
namespace boost {
 
19 +
namespace urls {
 
20 +

 
21 +
//------------------------------------------------
 
22 +

 
23 +
inline
 
24 +
url::
 
25 +
~url()
 
26 +
{
 
27 +
    if(s_)
 
28 +
    {
 
29 +
        BOOST_ASSERT(
 
30 +
            cap_ != 0);
 
31 +
        deallocate(s_);
 
32 +
    }
 
33 +
}
 
34 +

 
35 +
// construct empty
 
36 +
inline
 
37 +
url::
 
38 +
url() noexcept = default;
 
39 +

 
40 +
inline
 
41 +
url::
 
42 +
url(url&& u) noexcept
 
43 +
    : url_base(u.impl_)
 
44 +
{
 
45 +
    s_ = u.s_;
 
46 +
    cap_ = u.cap_;
 
47 +
    u.s_ = nullptr;
 
48 +
    u.cap_ = 0;
 
49 +
    u.impl_ = {from::url};
 
50 +
}
 
51 +

 
52 +
inline
 
53 +
url&
 
54 +
url::
 
55 +
operator=(url&& u) noexcept
 
56 +
{
 
57 +
    if(s_)
 
58 +
        deallocate(s_);
 
59 +
    impl_ = u.impl_;
 
60 +
    s_ = u.s_;
 
61 +
    cap_ = u.cap_;
 
62 +
    u.s_ = nullptr;
 
63 +
    u.cap_ = 0;
 
64 +
    u.impl_ = {from::url};
 
65 +
    return *this;
 
66 +
}
 
67 +

 
68 +
//------------------------------------------------
 
69 +

 
70 +
inline
 
71 +
char*
 
72 +
url::
 
73 +
allocate(std::size_t n)
 
74 +
{
 
75 +
    auto s = new char[n + 1];
 
76 +
    cap_ = n;
 
77 +
    return s;
 
78 +
}
 
79 +

 
80 +
inline
 
81 +
void
 
82 +
url::
 
83 +
deallocate(char* s)
 
84 +
{
 
85 +
    delete[] s;
 
86 +
}
 
87 +

 
88 +
inline
 
89 +
void
 
90 +
url::
 
91 +
clear_impl() noexcept
 
92 +
{
 
93 +
    if(s_)
 
94 +
    {
 
95 +
        // preserve capacity
 
96 +
        impl_ = {from::url};
 
97 +
        s_[0] = '\0';
 
98 +
        impl_.cs_ = s_;
 
99 +
    }
 
100 +
    else
 
101 +
    {
 
102 +
        BOOST_ASSERT(impl_.cs_[0] == 0);
 
103 +
    }
 
104 +
}
 
105 +

 
106 +
inline
 
107 +
void
 
108 +
url::
 
109 +
reserve_impl(
 
110 +
    std::size_t n,
 
111 +
    op_t& op)
 
112 +
{
 
113 +
    if(n > max_size())
 
114 +
        detail::throw_length_error();
 
115 +
    if(n <= cap_)
 
116 +
        return;
 
117 +
    char* s;
 
118 +
    if(s_ != nullptr)
 
119 +
    {
 
120 +
        // 50% growth policy
 
121 +
        auto const h = cap_ / 2;
 
122 +
        std::size_t new_cap;
 
123 +
        if(cap_ <= max_size() - h)
 
124 +
            new_cap = cap_ + h;
 
125 +
        else
 
126 +
            new_cap = max_size();
 
127 +
        if( new_cap < n)
 
128 +
            new_cap = n;
 
129 +
        s = allocate(new_cap);
 
130 +
        std::memcpy(s, s_, size() + 1);
 
131 +
        BOOST_ASSERT(! op.old);
 
132 +
        op.old = s_;
 
133 +
        s_ = s;
 
134 +
    }
 
135 +
    else
 
136 +
    {
 
137 +
        s_ = allocate(n);
 
138 +
        s_[0] = '\0';
 
139 +
    }
 
140 +
    impl_.cs_ = s_;
 
141 +
}
 
142 +

 
143 +
inline
 
144 +
void
 
145 +
url::
 
146 +
cleanup(
 
147 +
    op_t& op)
 
148 +
{
 
149 +
    if(op.old)
 
150 +
        deallocate(op.old);
 
151 +
}
 
152 +

 
153 +
//------------------------------------------------
 
154 +

 
155 +
inline
 
156 +
void
 
157 +
url::
 
158 +
swap(url& other) noexcept
 
159 +
{
 
160 +
    if (this == &other)
 
161 +
        return;
 
162 +
    std::swap(s_, other.s_);
 
163 +
    std::swap(cap_, other.cap_);
 
164 +
    std::swap(impl_, other.impl_);
 
165 +
    std::swap(external_impl_, other.external_impl_);
 
166 +
}
 
167 +

 
168 +
inline
 
169 +
url::
 
170 +
url(core::string_view s)
 
171 +
    : url(parse_uri_reference(s
 
172 +
        ).value(BOOST_URL_POS))
 
173 +
{
 
174 +
}
 
175 +

 
176 +
} // urls
 
177 +
} // boost
 
178 +

 
179 +
#endif