GCC Code Coverage Report
Directory: ../ Exec Total Coverage
File: /home/iojs/build/workspace/node-test-commit-linux-coverage-daily/nodes/benchmark/out/../src/node_http_common-inl.h Lines: 63 82 76.8 %
Date: 2020-05-27 22:15:15 Branches: 15 26 57.7 %

Line Branch Exec Source
1
#ifndef SRC_NODE_HTTP_COMMON_INL_H_
2
#define SRC_NODE_HTTP_COMMON_INL_H_
3
4
#include "node_http_common.h"
5
#include "node.h"
6
#include "node_mem-inl.h"
7
#include "env-inl.h"
8
#include "v8.h"
9
10
#include <algorithm>
11
12
namespace node {
13
14
template <typename T>
15
23565
NgHeaders<T>::NgHeaders(Environment* env, v8::Local<v8::Array> headers) {
16
  v8::Local<v8::Value> header_string =
17
70695
      headers->Get(env->context(), 0).ToLocalChecked();
18
  v8::Local<v8::Value> header_count =
19
70695
      headers->Get(env->context(), 1).ToLocalChecked();
20
23565
  CHECK(header_count->IsUint32());
21
47130
  CHECK(header_string->IsString());
22
47130
  count_ = header_count.As<v8::Uint32>()->Value();
23
47130
  int header_string_len = header_string.As<v8::String>()->Length();
24
25
23565
  if (count_ == 0) {
26
23
    CHECK_EQ(header_string_len, 0);
27
47
    return;
28
  }
29
30
23542
  buf_.AllocateSufficientStorage((alignof(nv_t) - 1) +
31
23542
                                 count_ * sizeof(nv_t) +
32
                                 header_string_len);
33
34
  char* start = reinterpret_cast<char*>(
35
23542
      RoundUp(reinterpret_cast<uintptr_t>(*buf_), alignof(nv_t)));
36
23542
  char* header_contents = start + (count_ * sizeof(nv_t));
37
23542
  nv_t* const nva = reinterpret_cast<nv_t*>(start);
38
39
23542
  CHECK_LE(header_contents + header_string_len, *buf_ + buf_.length());
40
70626
  CHECK_EQ(header_string.As<v8::String>()->WriteOneByte(
41
               env->isolate(),
42
               reinterpret_cast<uint8_t*>(header_contents),
43
               0,
44
               header_string_len,
45
               v8::String::NO_NULL_TERMINATION),
46
           header_string_len);
47
48
23542
  size_t n = 0;
49
  char* p;
50
95590
  for (p = header_contents; p < header_contents + header_string_len; n++) {
51
72049
    if (n >= count_) {
52
      static uint8_t zero = '\0';
53
1
      nva[0].name = nva[0].value = &zero;
54
1
      nva[0].namelen = nva[0].valuelen = 1;
55
1
      count_ = 1;
56
1
      return;
57
    }
58
59
72048
    nva[n].flags = T::kNoneFlag;
60
72048
    nva[n].name = reinterpret_cast<uint8_t*>(p);
61
72048
    nva[n].namelen = strlen(p);
62
72048
    p += nva[n].namelen + 1;
63
72048
    nva[n].value = reinterpret_cast<uint8_t*>(p);
64
72048
    nva[n].valuelen = strlen(p);
65
72048
    p += nva[n].valuelen + 1;
66
  }
67
}
68
69
294
size_t GetClientMaxHeaderPairs(size_t max_header_pairs) {
70
  static constexpr size_t min_header_pairs = 1;
71
294
  return std::max(max_header_pairs, min_header_pairs);
72
}
73
74
307
size_t GetServerMaxHeaderPairs(size_t max_header_pairs) {
75
  static constexpr size_t min_header_pairs = 4;
76
307
  return std::max(max_header_pairs, min_header_pairs);
77
}
78
79
template <typename allocator_t>
80
std::string NgHeaderBase<allocator_t>::ToString() const {
81
  std::string ret = name();
82
  ret += " = ";
83
  ret += value();
84
  return ret;
85
}
86
87
template <typename T>
88
bool NgHeader<T>::IsZeroLength(
89
    NgHeader<T>::rcbuf_t* name,
90
    NgHeader<T>::rcbuf_t* value) {
91
  return IsZeroLength(-1, name, value);
92
}
93
94
template <typename T>
95
bool NgHeader<T>::IsZeroLength(
96
    int32_t token,
97
    NgHeader<T>::rcbuf_t* name,
98
    NgHeader<T>::rcbuf_t* value) {
99
100
  if (NgHeader<T>::rcbufferpointer_t::IsZeroLength(value))
101
    return true;
102
103
  const char* header_name = T::ToHttpHeaderName(token);
104
  return header_name != nullptr ||
105
      NgHeader<T>::rcbufferpointer_t::IsZeroLength(name);
106
}
107
108
template <typename T>
109
71983
NgHeader<T>::NgHeader(
110
    Environment* env,
111
    NgHeader<T>::rcbuf_t* name,
112
    NgHeader<T>::rcbuf_t* value,
113
    uint8_t flags)
114
71983
    : NgHeader<T>(env, -1, name, value, flags) {}
115
116
template <typename T>
117
71983
NgHeader<T>::NgHeader(
118
    Environment* env,
119
    int32_t token,
120
    NgHeader<T>::rcbuf_t* name,
121
    NgHeader<T>::rcbuf_t* value,
122
71983
    uint8_t flags) : env_(env), token_(token), flags_(flags) {
123
71983
  if (token == -1) {
124
71983
    CHECK_NOT_NULL(name);
125
71983
    name_.reset(name, true);  // Internalizable
126
  }
127
71983
  CHECK_NOT_NULL(value);
128
71983
  name_.reset(name, true);  // Internalizable
129
71983
  value_.reset(value);
130
71983
}
131
132
template <typename T>
133
72005
NgHeader<T>::NgHeader(NgHeader<T>&& other) noexcept
134
72005
    : name_(std::move(other.name_)),
135
72005
      value_(std::move(other.value_)),
136
72005
      token_(other.token_),
137
288020
      flags_(other.flags_) {
138
72005
  other.token_ = -1;
139
72005
  other.flags_ = 0;
140
72005
  other.env_ = nullptr;
141
72005
}
142
143
template <typename T>
144
void NgHeader<T>::MemoryInfo(MemoryTracker* tracker) const {
145
  tracker->TrackField("name", name_);
146
  tracker->TrackField("value", value_);
147
}
148
149
template <typename T>
150
71872
v8::MaybeLocal<v8::String> NgHeader<T>::GetName(
151
    NgHeader<T>::allocator_t* allocator) const {
152
153
  // Not all instances will support using token id's for header names.
154
  // HTTP/2 specifically does not support it.
155
71872
  const char* header_name = T::ToHttpHeaderName(token_);
156
157
  // If header_name is not nullptr, then it is a known header with
158
  // a statically defined name. We can safely internalize it here.
159
71872
  if (header_name != nullptr) {
160
    auto& static_str_map = env_->isolate_data()->static_str_map;
161
    v8::Eternal<v8::String> eternal = static_str_map[header_name];
162
    if (eternal.IsEmpty()) {
163
      v8::Local<v8::String> str = OneByteString(env_->isolate(), header_name);
164
      eternal.Set(env_->isolate(), str);
165
      return str;
166
    }
167
    return eternal.Get(env_->isolate());
168
  }
169
71872
  return rcbufferpointer_t::External::New(allocator, name_);
170
}
171
172
template <typename T>
173
71872
v8::MaybeLocal<v8::String> NgHeader<T>::GetValue(
174
    NgHeader<T>::allocator_t* allocator) const {
175
71872
  return rcbufferpointer_t::External::New(allocator, value_);
176
}
177
178
template <typename T>
179
std::string NgHeader<T>::name() const {
180
  return name_.str();
181
}
182
183
template <typename T>
184
std::string NgHeader<T>::value() const {
185
  return value_.str();
186
}
187
188
template <typename T>
189
71983
size_t NgHeader<T>::length() const {
190
71983
  return name_.len() + value_.len();
191
}
192
193
}  // namespace node
194
195
#endif  // SRC_NODE_HTTP_COMMON_INL_H_