Coverage Report

Created: 2018-07-19 03:59

/Users/buildslave/jenkins/workspace/clang-stage2-coverage-R/llvm/include/llvm/ADT/StringExtras.h
Line
Count
Source (jump to first uncovered line)
1
//===- llvm/ADT/StringExtras.h - Useful string functions --------*- C++ -*-===//
2
//
3
//                     The LLVM Compiler Infrastructure
4
//
5
// This file is distributed under the University of Illinois Open Source
6
// License. See LICENSE.TXT for details.
7
//
8
//===----------------------------------------------------------------------===//
9
//
10
// This file contains some functions that are useful when dealing with strings.
11
//
12
//===----------------------------------------------------------------------===//
13
14
#ifndef LLVM_ADT_STRINGEXTRAS_H
15
#define LLVM_ADT_STRINGEXTRAS_H
16
17
#include "llvm/ADT/ArrayRef.h"
18
#include "llvm/ADT/SmallString.h"
19
#include "llvm/ADT/StringRef.h"
20
#include "llvm/ADT/Twine.h"
21
#include <cassert>
22
#include <cstddef>
23
#include <cstdint>
24
#include <cstdlib>
25
#include <cstring>
26
#include <iterator>
27
#include <string>
28
#include <utility>
29
30
namespace llvm {
31
32
template<typename T> class SmallVectorImpl;
33
class raw_ostream;
34
35
/// hexdigit - Return the hexadecimal character for the
36
/// given number \p X (which should be less than 16).
37
48.0M
inline char hexdigit(unsigned X, bool LowerCase = false) {
38
48.0M
  const char HexChar = LowerCase ? 
'a'1.12M
:
'A'46.8M
;
39
48.0M
  return X < 10 ? 
'0' + X44.1M
:
HexChar + X - 103.82M
;
40
48.0M
}
41
42
/// Given an array of c-style strings terminated by a null pointer, construct
43
/// a vector of StringRefs representing the same strings without the terminating
44
/// null string.
45
17.9k
inline std::vector<StringRef> toStringRefArray(const char *const *Strings) {
46
17.9k
  std::vector<StringRef> Result;
47
1.22M
  while (*Strings)
48
1.20M
    Result.push_back(*Strings++);
49
17.9k
  return Result;
50
17.9k
}
51
52
/// Construct a string ref from a boolean.
53
4.05M
inline StringRef toStringRef(bool B) { return StringRef(B ? 
"true"4.03k
:
"false"4.05M
); }
54
55
/// Construct a string ref from an array ref of unsigned chars.
56
5.84k
inline StringRef toStringRef(ArrayRef<uint8_t> Input) {
57
5.84k
  return StringRef(reinterpret_cast<const char *>(Input.begin()), Input.size());
58
5.84k
}
59
60
/// Construct a string ref from an array ref of unsigned chars.
61
10.3k
inline ArrayRef<uint8_t> arrayRefFromStringRef(StringRef Input) {
62
10.3k
  return {Input.bytes_begin(), Input.bytes_end()};
63
10.3k
}
64
65
/// Interpret the given character \p C as a hexadecimal digit and return its
66
/// value.
67
///
68
/// If \p C is not a valid hex digit, -1U is returned.
69
14.1M
inline unsigned hexDigitValue(char C) {
70
14.1M
  if (C >= '0' && 
C <= '9'13.7M
)
return C-'0'13.0M
;
71
1.10M
  if (C >= 'a' && 
C <= 'f'309k
)
return C-'a'+10U295k
;
72
808k
  if (C >= 'A' && 
C <= 'F'284k
)
return C-'A'+10U135k
;
73
673k
  return -1U;
74
673k
}
75
76
/// Checks if character \p C is one of the 10 decimal digits.
77
14.0M
inline bool isDigit(char C) { return C >= '0' && 
C <= '9'10.4M
; }
78
79
/// Checks if character \p C is a hexadecimal numeric character.
80
843k
inline bool isHexDigit(char C) { return hexDigitValue(C) != -1U; }
81
82
/// Checks if character \p C is a valid letter as classified by "C" locale.
83
40.0M
inline bool isAlpha(char C) {
84
40.0M
  return ('a' <= C && 
C <= 'z'32.2M
) ||
(7.89M
'A' <= C7.89M
&&
C <= 'Z'2.33M
);
85
40.0M
}
86
87
/// Checks whether character \p C is either a decimal digit or an uppercase or
88
/// lowercase letter as classified by "C" locale.
89
39.8M
inline bool isAlnum(char C) { return isAlpha(C) || 
isDigit(C)6.74M
; }
90
91
/// Checks whether character \p C is valid ASCII (high bit is zero).
92
inline bool isASCII(char C) { return static_cast<unsigned char>(C) <= 127; }
93
94
/// Checks whether all characters in S are ASCII.
95
inline bool isASCII(llvm::StringRef S) {
96
  for (char C : S)
97
    if (LLVM_UNLIKELY(!isASCII(C)))
98
      return false;
99
  return true;
100
}
101
102
/// Returns the corresponding lowercase character if \p x is uppercase.
103
198M
inline char toLower(char x) {
104
198M
  if (x >= 'A' && 
x <= 'Z'150M
)
105
82.3M
    return x - 'A' + 'a';
106
116M
  return x;
107
116M
}
108
109
/// Returns the corresponding uppercase character if \p x is lowercase.
110
1.56M
inline char toUpper(char x) {
111
1.56M
  if (x >= 'a' && 
x <= 'z'1.08M
)
112
1.07M
    return x - 'a' + 'A';
113
483k
  return x;
114
483k
}
115
116
8.05k
inline std::string utohexstr(uint64_t X, bool LowerCase = false) {
117
8.05k
  char Buffer[17];
118
8.05k
  char *BufPtr = std::end(Buffer);
119
8.05k
120
8.05k
  if (X == 0) 
*--BufPtr = '0'280
;
121
8.05k
122
33.1k
  while (X) {
123
25.0k
    unsigned char Mod = static_cast<unsigned char>(X) & 15;
124
25.0k
    *--BufPtr = hexdigit(Mod, LowerCase);
125
25.0k
    X >>= 4;
126
25.0k
  }
127
8.05k
128
8.05k
  return std::string(BufPtr, std::end(Buffer));
129
8.05k
}
130
131
/// Convert buffer \p Input to its hexadecimal representation.
132
/// The returned string is double the size of \p Input.
133
461
inline std::string toHex(StringRef Input) {
134
461
  static const char *const LUT = "0123456789ABCDEF";
135
461
  size_t Length = Input.size();
136
461
137
461
  std::string Output;
138
461
  Output.reserve(2 * Length);
139
8.04k
  for (size_t i = 0; i < Length; 
++i7.57k
) {
140
7.57k
    const unsigned char c = Input[i];
141
7.57k
    Output.push_back(LUT[c >> 4]);
142
7.57k
    Output.push_back(LUT[c & 15]);
143
7.57k
  }
144
461
  return Output;
145
461
}
146
147
361
inline std::string toHex(ArrayRef<uint8_t> Input) {
148
361
  return toHex(toStringRef(Input));
149
361
}
150
151
2.44k
inline uint8_t hexFromNibbles(char MSB, char LSB) {
152
2.44k
  unsigned U1 = hexDigitValue(MSB);
153
2.44k
  unsigned U2 = hexDigitValue(LSB);
154
2.44k
  assert(U1 != -1U && U2 != -1U);
155
2.44k
156
2.44k
  return static_cast<uint8_t>((U1 << 4) | U2);
157
2.44k
}
158
159
/// Convert hexadecimal string \p Input to its binary representation.
160
/// The return string is half the size of \p Input.
161
174
inline std::string fromHex(StringRef Input) {
162
174
  if (Input.empty())
163
20
    return std::string();
164
154
165
154
  std::string Output;
166
154
  Output.reserve((Input.size() + 1) / 2);
167
154
  if (Input.size() % 2 == 1) {
168
1
    Output.push_back(hexFromNibbles('0', Input.front()));
169
1
    Input = Input.drop_front();
170
1
  }
171
154
172
154
  assert(Input.size() % 2 == 0);
173
2.59k
  while (!Input.empty()) {
174
2.44k
    uint8_t Hex = hexFromNibbles(Input[0], Input[1]);
175
2.44k
    Output.push_back(Hex);
176
2.44k
    Input = Input.drop_front(2);
177
2.44k
  }
178
154
  return Output;
179
154
}
180
181
/// Convert the string \p S to an integer of the specified type using
182
/// the radix \p Base.  If \p Base is 0, auto-detects the radix.
183
/// Returns true if the number was successfully converted, false otherwise.
184
2.43k
template <typename N> bool to_integer(StringRef S, N &Num, unsigned Base = 0) {
185
2.43k
  return !S.getAsInteger(Base, Num);
186
2.43k
}
bool llvm::to_integer<unsigned int>(llvm::StringRef, unsigned int&, unsigned int)
Line
Count
Source
184
500
template <typename N> bool to_integer(StringRef S, N &Num, unsigned Base = 0) {
185
500
  return !S.getAsInteger(Base, Num);
186
500
}
bool llvm::to_integer<unsigned long long>(llvm::StringRef, unsigned long long&, unsigned int)
Line
Count
Source
184
1.87k
template <typename N> bool to_integer(StringRef S, N &Num, unsigned Base = 0) {
185
1.87k
  return !S.getAsInteger(Base, Num);
186
1.87k
}
bool llvm::to_integer<int>(llvm::StringRef, int&, unsigned int)
Line
Count
Source
184
53
template <typename N> bool to_integer(StringRef S, N &Num, unsigned Base = 0) {
185
53
  return !S.getAsInteger(Base, Num);
186
53
}
bool llvm::to_integer<unsigned char>(llvm::StringRef, unsigned char&, unsigned int)
Line
Count
Source
184
12
template <typename N> bool to_integer(StringRef S, N &Num, unsigned Base = 0) {
185
12
  return !S.getAsInteger(Base, Num);
186
12
}
187
188
namespace detail {
189
template <typename N>
190
46
inline bool to_float(const Twine &T, N &Num, N (*StrTo)(const char *, char **)) {
191
46
  SmallString<32> Storage;
192
46
  StringRef S = T.toNullTerminatedStringRef(Storage);
193
46
  char *End;
194
46
  N Temp = StrTo(S.data(), &End);
195
46
  if (*End != '\0')
196
4
    return false;
197
42
  Num = Temp;
198
42
  return true;
199
42
}
bool llvm::detail::to_float<double>(llvm::Twine const&, double&, double (*)(char const*, char**))
Line
Count
Source
190
35
inline bool to_float(const Twine &T, N &Num, N (*StrTo)(const char *, char **)) {
191
35
  SmallString<32> Storage;
192
35
  StringRef S = T.toNullTerminatedStringRef(Storage);
193
35
  char *End;
194
35
  N Temp = StrTo(S.data(), &End);
195
35
  if (*End != '\0')
196
1
    return false;
197
34
  Num = Temp;
198
34
  return true;
199
34
}
bool llvm::detail::to_float<float>(llvm::Twine const&, float&, float (*)(char const*, char**))
Line
Count
Source
190
11
inline bool to_float(const Twine &T, N &Num, N (*StrTo)(const char *, char **)) {
191
11
  SmallString<32> Storage;
192
11
  StringRef S = T.toNullTerminatedStringRef(Storage);
193
11
  char *End;
194
11
  N Temp = StrTo(S.data(), &End);
195
11
  if (*End != '\0')
196
3
    return false;
197
8
  Num = Temp;
198
8
  return true;
199
8
}
200
}
201
202
11
inline bool to_float(const Twine &T, float &Num) {
203
11
  return detail::to_float(T, Num, strtof);
204
11
}
205
206
35
inline bool to_float(const Twine &T, double &Num) {
207
35
  return detail::to_float(T, Num, strtod);
208
35
}
209
210
inline bool to_float(const Twine &T, long double &Num) {
211
  return detail::to_float(T, Num, strtold);
212
}
213
214
7.44M
inline std::string utostr(uint64_t X, bool isNeg = false) {
215
7.44M
  char Buffer[21];
216
7.44M
  char *BufPtr = std::end(Buffer);
217
7.44M
218
7.44M
  if (X == 0) 
*--BufPtr = '0'1.44M
; // Handle special case...
219
7.44M
220
17.5M
  while (X) {
221
10.0M
    *--BufPtr = '0' + char(X % 10);
222
10.0M
    X /= 10;
223
10.0M
  }
224
7.44M
225
7.44M
  if (isNeg) 
*--BufPtr = '-'91.6k
; // Add negative sign...
226
7.44M
  return std::string(BufPtr, std::end(Buffer));
227
7.44M
}
228
229
1.38M
inline std::string itostr(int64_t X) {
230
1.38M
  if (X < 0)
231
91.6k
    return utostr(static_cast<uint64_t>(-X), true);
232
1.29M
  else
233
1.29M
    return utostr(static_cast<uint64_t>(X));
234
1.38M
}
235
236
/// StrInStrNoCase - Portable version of strcasestr.  Locates the first
237
/// occurrence of string 's1' in string 's2', ignoring case.  Returns
238
/// the offset of s2 in s1 or npos if s2 cannot be found.
239
StringRef::size_type StrInStrNoCase(StringRef s1, StringRef s2);
240
241
/// getToken - This function extracts one token from source, ignoring any
242
/// leading characters that appear in the Delimiters string, and ending the
243
/// token at any of the characters that appear in the Delimiters string.  If
244
/// there are no tokens in the source string, an empty string is returned.
245
/// The function returns a pair containing the extracted token and the
246
/// remaining tail string.
247
std::pair<StringRef, StringRef> getToken(StringRef Source,
248
                                         StringRef Delimiters = " \t\n\v\f\r");
249
250
/// SplitString - Split up the specified string according to the specified
251
/// delimiters, appending the result fragments to the output list.
252
void SplitString(StringRef Source,
253
                 SmallVectorImpl<StringRef> &OutFragments,
254
                 StringRef Delimiters = " \t\n\v\f\r");
255
256
/// Returns the English suffix for an ordinal integer (-st, -nd, -rd, -th).
257
5.76k
inline StringRef getOrdinalSuffix(unsigned Val) {
258
5.76k
  // It is critically important that we do this perfectly for
259
5.76k
  // user-written sequences with over 100 elements.
260
5.76k
  switch (Val % 100) {
261
5.76k
  case 11:
262
0
  case 12:
263
0
  case 13:
264
0
    return "th";
265
5.76k
  default:
266
5.76k
    switch (Val % 10) {
267
5.76k
      
case 1: return "st"5.38k
;
268
5.76k
      
case 2: return "nd"259
;
269
5.76k
      
case 3: return "rd"108
;
270
5.76k
      
default: return "th"15
;
271
5.76k
    }
272
5.76k
  }
273
5.76k
}
274
275
/// Print each character of the specified string, escaping it if it is not
276
/// printable or if it is an escape char.
277
void printEscapedString(StringRef Name, raw_ostream &Out);
278
279
/// Print each character of the specified string, escaping HTML special
280
/// characters.
281
void printHTMLEscaped(StringRef String, raw_ostream &Out);
282
283
/// printLowerCase - Print each character as lowercase if it is uppercase.
284
void printLowerCase(StringRef String, raw_ostream &Out);
285
286
namespace detail {
287
288
template <typename IteratorT>
289
inline std::string join_impl(IteratorT Begin, IteratorT End,
290
                             StringRef Separator, std::input_iterator_tag) {
291
  std::string S;
292
  if (Begin == End)
293
    return S;
294
295
  S += (*Begin);
296
  while (++Begin != End) {
297
    S += Separator;
298
    S += (*Begin);
299
  }
300
  return S;
301
}
302
303
template <typename IteratorT>
304
inline std::string join_impl(IteratorT Begin, IteratorT End,
305
791k
                             StringRef Separator, std::forward_iterator_tag) {
306
791k
  std::string S;
307
791k
  if (Begin == End)
308
22.9k
    return S;
309
768k
310
768k
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
6.45M
  for (IteratorT I = Begin; I != End; 
++I5.68M
)
312
5.68M
    Len += (*Begin).size();
313
768k
  S.reserve(Len);
314
768k
  S += (*Begin);
315
5.68M
  while (++Begin != End) {
316
4.91M
    S += Separator;
317
4.91M
    S += (*Begin);
318
4.91M
  }
319
768k
  return S;
320
768k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::detail::join_impl<std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*> >(std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*>, std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*>, llvm::StringRef, std::__1::forward_iterator_tag)
Line
Count
Source
305
733k
                             StringRef Separator, std::forward_iterator_tag) {
306
733k
  std::string S;
307
733k
  if (Begin == End)
308
4
    return S;
309
733k
310
733k
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
6.26M
  for (IteratorT I = Begin; I != End; 
++I5.53M
)
312
5.53M
    Len += (*Begin).size();
313
733k
  S.reserve(Len);
314
733k
  S += (*Begin);
315
5.53M
  while (++Begin != End) {
316
4.79M
    S += Separator;
317
4.79M
    S += (*Begin);
318
4.79M
  }
319
733k
  return S;
320
733k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::detail::join_impl<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*>(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*, llvm::StringRef, std::__1::forward_iterator_tag)
Line
Count
Source
305
2.39k
                             StringRef Separator, std::forward_iterator_tag) {
306
2.39k
  std::string S;
307
2.39k
  if (Begin == End)
308
24
    return S;
309
2.37k
310
2.37k
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
4.94k
  for (IteratorT I = Begin; I != End; 
++I2.57k
)
312
2.57k
    Len += (*Begin).size();
313
2.37k
  S.reserve(Len);
314
2.37k
  S += (*Begin);
315
2.57k
  while (++Begin != End) {
316
197
    S += Separator;
317
197
    S += (*Begin);
318
197
  }
319
2.37k
  return S;
320
2.37k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::detail::join_impl<llvm::StringRef*>(llvm::StringRef*, llvm::StringRef*, llvm::StringRef, std::__1::forward_iterator_tag)
Line
Count
Source
305
3.39k
                             StringRef Separator, std::forward_iterator_tag) {
306
3.39k
  std::string S;
307
3.39k
  if (Begin == End)
308
1.12k
    return S;
309
2.26k
310
2.26k
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
8.72k
  for (IteratorT I = Begin; I != End; 
++I6.46k
)
312
6.46k
    Len += (*Begin).size();
313
2.26k
  S.reserve(Len);
314
2.26k
  S += (*Begin);
315
6.46k
  while (++Begin != End) {
316
4.19k
    S += Separator;
317
4.19k
    S += (*Begin);
318
4.19k
  }
319
2.26k
  return S;
320
2.26k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::detail::join_impl<std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*> >(std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*>, std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*>, llvm::StringRef, std::__1::forward_iterator_tag)
Line
Count
Source
305
48.1k
                             StringRef Separator, std::forward_iterator_tag) {
306
48.1k
  std::string S;
307
48.1k
  if (Begin == End)
308
19.3k
    return S;
309
28.8k
310
28.8k
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
167k
  for (IteratorT I = Begin; I != End; 
++I139k
)
312
139k
    Len += (*Begin).size();
313
28.8k
  S.reserve(Len);
314
28.8k
  S += (*Begin);
315
139k
  while (++Begin != End) {
316
110k
    S += Separator;
317
110k
    S += (*Begin);
318
110k
  }
319
28.8k
  return S;
320
28.8k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::detail::join_impl<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*>(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*, llvm::StringRef, std::__1::forward_iterator_tag)
Line
Count
Source
305
799
                             StringRef Separator, std::forward_iterator_tag) {
306
799
  std::string S;
307
799
  if (Begin == End)
308
0
    return S;
309
799
310
799
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
2.41k
  for (IteratorT I = Begin; I != End; 
++I1.61k
)
312
1.61k
    Len += (*Begin).size();
313
799
  S.reserve(Len);
314
799
  S += (*Begin);
315
1.61k
  while (++Begin != End) {
316
820
    S += Separator;
317
820
    S += (*Begin);
318
820
  }
319
799
  return S;
320
799
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::detail::join_impl<std::__1::__wrap_iter<llvm::StringRef*> >(std::__1::__wrap_iter<llvm::StringRef*>, std::__1::__wrap_iter<llvm::StringRef*>, llvm::StringRef, std::__1::forward_iterator_tag)
Line
Count
Source
305
3.02k
                             StringRef Separator, std::forward_iterator_tag) {
306
3.02k
  std::string S;
307
3.02k
  if (Begin == End)
308
2.41k
    return S;
309
614
310
614
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
3.58k
  for (IteratorT I = Begin; I != End; 
++I2.97k
)
312
2.97k
    Len += (*Begin).size();
313
614
  S.reserve(Len);
314
614
  S += (*Begin);
315
2.97k
  while (++Begin != End) {
316
2.35k
    S += Separator;
317
2.35k
    S += (*Begin);
318
2.35k
  }
319
614
  return S;
320
614
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::detail::join_impl<llvm::StringRef const*>(llvm::StringRef const*, llvm::StringRef const*, llvm::StringRef, std::__1::forward_iterator_tag)
Line
Count
Source
305
72
                             StringRef Separator, std::forward_iterator_tag) {
306
72
  std::string S;
307
72
  if (Begin == End)
308
0
    return S;
309
72
310
72
  size_t Len = (std::distance(Begin, End) - 1) * Separator.size();
311
526
  for (IteratorT I = Begin; I != End; 
++I454
)
312
454
    Len += (*Begin).size();
313
72
  S.reserve(Len);
314
72
  S += (*Begin);
315
454
  while (++Begin != End) {
316
382
    S += Separator;
317
382
    S += (*Begin);
318
382
  }
319
72
  return S;
320
72
}
321
322
template <typename Sep>
323
inline void join_items_impl(std::string &Result, Sep Separator) {}
324
325
template <typename Sep, typename Arg>
326
inline void join_items_impl(std::string &Result, Sep Separator,
327
                            const Arg &Item) {
328
  Result += Item;
329
}
330
331
template <typename Sep, typename Arg1, typename... Args>
332
inline void join_items_impl(std::string &Result, Sep Separator, const Arg1 &A1,
333
                            Args &&... Items) {
334
  Result += A1;
335
  Result += Separator;
336
  join_items_impl(Result, Separator, std::forward<Args>(Items)...);
337
}
338
339
inline size_t join_one_item_size(char C) { return 1; }
340
inline size_t join_one_item_size(const char *S) { return S ? ::strlen(S) : 0; }
341
342
template <typename T> inline size_t join_one_item_size(const T &Str) {
343
  return Str.size();
344
}
345
346
inline size_t join_items_size() { return 0; }
347
348
template <typename A1> inline size_t join_items_size(const A1 &A) {
349
  return join_one_item_size(A);
350
}
351
template <typename A1, typename... Args>
352
inline size_t join_items_size(const A1 &A, Args &&... Items) {
353
  return join_one_item_size(A) + join_items_size(std::forward<Args>(Items)...);
354
}
355
356
} // end namespace detail
357
358
/// Joins the strings in the range [Begin, End), adding Separator between
359
/// the elements.
360
template <typename IteratorT>
361
791k
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
791k
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
791k
  return detail::join_impl(Begin, End, Separator, tag());
364
791k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*> >(std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*>, std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*>, llvm::StringRef)
Line
Count
Source
361
733k
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
733k
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
733k
  return detail::join_impl(Begin, End, Separator, tag());
364
733k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*>(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >*, llvm::StringRef)
Line
Count
Source
361
2.39k
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
2.39k
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
2.39k
  return detail::join_impl(Begin, End, Separator, tag());
364
2.39k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<llvm::StringRef*>(llvm::StringRef*, llvm::StringRef*, llvm::StringRef)
Line
Count
Source
361
3.39k
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
3.39k
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
3.39k
  return detail::join_impl(Begin, End, Separator, tag());
364
3.39k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*> >(std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*>, std::__1::__wrap_iter<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*>, llvm::StringRef)
Line
Count
Source
361
48.1k
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
48.1k
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
48.1k
  return detail::join_impl(Begin, End, Separator, tag());
364
48.1k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*>(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const*, llvm::StringRef)
Line
Count
Source
361
799
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
799
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
799
  return detail::join_impl(Begin, End, Separator, tag());
364
799
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<std::__1::__wrap_iter<llvm::StringRef*> >(std::__1::__wrap_iter<llvm::StringRef*>, std::__1::__wrap_iter<llvm::StringRef*>, llvm::StringRef)
Line
Count
Source
361
3.02k
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
3.02k
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
3.02k
  return detail::join_impl(Begin, End, Separator, tag());
364
3.02k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<llvm::StringRef const*>(llvm::StringRef const*, llvm::StringRef const*, llvm::StringRef)
Line
Count
Source
361
72
inline std::string join(IteratorT Begin, IteratorT End, StringRef Separator) {
362
72
  using tag = typename std::iterator_traits<IteratorT>::iterator_category;
363
72
  return detail::join_impl(Begin, End, Separator, tag());
364
72
}
365
366
/// Joins the strings in the range [R.begin(), R.end()), adding Separator
367
/// between the elements.
368
template <typename Range>
369
733k
inline std::string join(Range &&R, StringRef Separator) {
370
733k
  return join(R.begin(), R.end(), Separator);
371
733k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<llvm::SmallVector<llvm::StringRef, 32u>&>(llvm::SmallVector<llvm::StringRef, 32u>&&&, llvm::StringRef)
Line
Count
Source
369
57
inline std::string join(Range &&R, StringRef Separator) {
370
57
  return join(R.begin(), R.end(), Separator);
371
57
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > const&>(std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > > const&&&, llvm::StringRef)
Line
Count
Source
369
1
inline std::string join(Range &&R, StringRef Separator) {
370
1
  return join(R.begin(), R.end(), Separator);
371
1
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >&>(std::__1::vector<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >, std::__1::allocator<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > > >&&&, llvm::StringRef)
Line
Count
Source
369
733k
inline std::string join(Range &&R, StringRef Separator) {
370
733k
  return join(R.begin(), R.end(), Separator);
371
733k
}
std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > llvm::join<llvm::ArrayRef<llvm::StringRef>&>(llvm::ArrayRef<llvm::StringRef>&&&, llvm::StringRef)
Line
Count
Source
369
72
inline std::string join(Range &&R, StringRef Separator) {
370
72
  return join(R.begin(), R.end(), Separator);
371
72
}
372
373
/// Joins the strings in the parameter pack \p Items, adding \p Separator
374
/// between the elements.  All arguments must be implicitly convertible to
375
/// std::string, or there should be an overload of std::string::operator+=()
376
/// that accepts the argument explicitly.
377
template <typename Sep, typename... Args>
378
inline std::string join_items(Sep Separator, Args &&... Items) {
379
  std::string Result;
380
  if (sizeof...(Items) == 0)
381
    return Result;
382
383
  size_t NS = detail::join_one_item_size(Separator);
384
  size_t NI = detail::join_items_size(std::forward<Args>(Items)...);
385
  Result.reserve(NI + (sizeof...(Items) - 1) * NS + 1);
386
  detail::join_items_impl(Result, Separator, std::forward<Args>(Items)...);
387
  return Result;
388
}
389
390
} // end namespace llvm
391
392
#endif // LLVM_ADT_STRINGEXTRAS_H