2 * nghttp2 - HTTP/2 C Library
4 * Copyright (c) 2014 Tatsuhiro Tsujikawa
6 * Permission is hereby granted, free of charge, to any person obtaining
7 * a copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sublicense, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
14 * The above copyright notice and this permission notice shall be
15 * included in all copies or substantial portions of the Software.
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
21 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
22 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
23 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25 #include "libevent_util.h"
34 EvbufferBuffer::EvbufferBuffer()
35 : evbuffer_(nullptr), bucket_(nullptr), buf_(nullptr), bufmax_(0),
36 buflen_(0), limit_(0), writelen_(0) {}
38 EvbufferBuffer::EvbufferBuffer(evbuffer *evbuffer, uint8_t *buf, size_t bufmax,
40 : evbuffer_(evbuffer), bucket_(limit == -1 ? nullptr : evbuffer_new()),
41 buf_(buf), bufmax_(bufmax), buflen_(0), limit_(limit), writelen_(0) {}
43 void EvbufferBuffer::reset(evbuffer *evbuffer, uint8_t *buf, size_t bufmax,
47 if (limit != -1 && !bucket_) {
48 bucket_ = evbuffer_new();
56 EvbufferBuffer::~EvbufferBuffer() {
58 evbuffer_free(bucket_);
62 int EvbufferBuffer::write_buffer() {
63 for (auto pos = buf_, end = buf_ + buflen_; pos < end;) {
64 // To avoid merging chunks in evbuffer, we first add to temporal
65 // buffer bucket_ and then move its chain to evbuffer_.
66 auto nwrite = std::min(end - pos, limit_);
67 auto rv = evbuffer_add(bucket_, pos, nwrite);
71 rv = evbuffer_add_buffer(evbuffer_, bucket_);
80 int EvbufferBuffer::flush() {
84 rv = evbuffer_add(evbuffer_, buf_, buflen_);
97 int EvbufferBuffer::add(const uint8_t *data, size_t datalen) {
99 if (buflen_ + datalen > bufmax_) {
102 rv = evbuffer_add(evbuffer_, buf_, buflen_);
109 writelen_ += buflen_;
112 if (datalen > bufmax_) {
114 rv = evbuffer_add(evbuffer_, data, datalen);
121 writelen_ += buflen_;
125 memcpy(buf_ + buflen_, data, datalen);
130 size_t EvbufferBuffer::get_buflen() const { return buflen_; }
132 size_t EvbufferBuffer::get_writelen() const { return writelen_; }
134 void bev_enable_unless(bufferevent *bev, int events) {
135 if ((bufferevent_get_enabled(bev) & events) == events) {
139 bufferevent_enable(bev, events);
142 void bev_disable_unless(bufferevent *bev, int events) {
143 if ((bufferevent_get_enabled(bev) & events) == 0) {
147 bufferevent_disable(bev, events);
152 } // namespace nghttp2