security/sandbox/chromium/base/strings/string_piece.cc

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

     1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
     2 // Use of this source code is governed by a BSD-style license that can be
     3 // found in the LICENSE file.
     4 // Copied from strings/stringpiece.cc with modifications
     6 #include "base/strings/string_piece.h"
     8 #include <algorithm>
     9 #include <ostream>
    11 namespace base {
    13 // MSVC doesn't like complex extern templates and DLLs.
    14 #if !defined(COMPILER_MSVC)
    15 namespace internal {
    16 template class StringPieceDetail<std::string>;
    17 template class StringPieceDetail<string16>;
    18 }  // namespace internal
    20 template class BasicStringPiece<string16>;
    21 #endif
    23 bool operator==(const StringPiece& x, const StringPiece& y) {
    24   if (x.size() != y.size())
    25     return false;
    27   return StringPiece::wordmemcmp(x.data(), y.data(), x.size()) == 0;
    28 }
    30 std::ostream& operator<<(std::ostream& o, const StringPiece& piece) {
    31   o.write(piece.data(), static_cast<std::streamsize>(piece.size()));
    32   return o;
    33 }
    35 namespace internal {
    36 void CopyToString(const StringPiece& self, std::string* target) {
    37   target->assign(!self.empty() ? self.data() : "", self.size());
    38 }
    40 void AppendToString(const StringPiece& self, std::string* target) {
    41   if (!self.empty())
    42     target->append(self.data(), self.size());
    43 }
    45 StringPiece::size_type copy(const StringPiece& self,
    46                             char* buf,
    47                             StringPiece::size_type n,
    48                             StringPiece::size_type pos) {
    49   StringPiece::size_type ret = std::min(self.size() - pos, n);
    50   memcpy(buf, self.data() + pos, ret);
    51   return ret;
    52 }
    54 StringPiece::size_type find(const StringPiece& self,
    55                             const StringPiece& s,
    56                             StringPiece::size_type pos) {
    57   if (pos > self.size())
    58     return StringPiece::npos;
    60   StringPiece::const_iterator result =
    61       std::search(self.begin() + pos, self.end(), s.begin(), s.end());
    62   const StringPiece::size_type xpos =
    63     static_cast<size_t>(result - self.begin());
    64   return xpos + s.size() <= self.size() ? xpos : StringPiece::npos;
    65 }
    67 StringPiece::size_type find(const StringPiece& self,
    68                             char c,
    69                             StringPiece::size_type pos) {
    70   if (pos >= self.size())
    71     return StringPiece::npos;
    73   StringPiece::const_iterator result =
    74       std::find(self.begin() + pos, self.end(), c);
    75   return result != self.end() ?
    76       static_cast<size_t>(result - self.begin()) : StringPiece::npos;
    77 }
    79 StringPiece::size_type rfind(const StringPiece& self,
    80                              const StringPiece& s,
    81                              StringPiece::size_type pos) {
    82   if (self.size() < s.size())
    83     return StringPiece::npos;
    85   if (s.empty())
    86     return std::min(self.size(), pos);
    88   StringPiece::const_iterator last =
    89       self.begin() + std::min(self.size() - s.size(), pos) + s.size();
    90   StringPiece::const_iterator result =
    91       std::find_end(self.begin(), last, s.begin(), s.end());
    92   return result != last ?
    93       static_cast<size_t>(result - self.begin()) : StringPiece::npos;
    94 }
    96 StringPiece::size_type rfind(const StringPiece& self,
    97                              char c,
    98                              StringPiece::size_type pos) {
    99   if (self.size() == 0)
   100     return StringPiece::npos;
   102   for (StringPiece::size_type i = std::min(pos, self.size() - 1); ; --i) {
   103     if (self.data()[i] == c)
   104       return i;
   105     if (i == 0)
   106       break;
   107   }
   108   return StringPiece::npos;
   109 }
   111 // For each character in characters_wanted, sets the index corresponding
   112 // to the ASCII code of that character to 1 in table.  This is used by
   113 // the find_.*_of methods below to tell whether or not a character is in
   114 // the lookup table in constant time.
   115 // The argument `table' must be an array that is large enough to hold all
   116 // the possible values of an unsigned char.  Thus it should be be declared
   117 // as follows:
   118 //   bool table[UCHAR_MAX + 1]
   119 static inline void BuildLookupTable(const StringPiece& characters_wanted,
   120                                     bool* table) {
   121   const StringPiece::size_type length = characters_wanted.length();
   122   const char* const data = characters_wanted.data();
   123   for (StringPiece::size_type i = 0; i < length; ++i) {
   124     table[static_cast<unsigned char>(data[i])] = true;
   125   }
   126 }
   128 StringPiece::size_type find_first_of(const StringPiece& self,
   129                                      const StringPiece& s,
   130                                      StringPiece::size_type pos) {
   131   if (self.size() == 0 || s.size() == 0)
   132     return StringPiece::npos;
   134   // Avoid the cost of BuildLookupTable() for a single-character search.
   135   if (s.size() == 1)
   136     return find(self, s.data()[0], pos);
   138   bool lookup[UCHAR_MAX + 1] = { false };
   139   BuildLookupTable(s, lookup);
   140   for (StringPiece::size_type i = pos; i < self.size(); ++i) {
   141     if (lookup[static_cast<unsigned char>(self.data()[i])]) {
   142       return i;
   143     }
   144   }
   145   return StringPiece::npos;
   146 }
   148 StringPiece::size_type find_first_not_of(const StringPiece& self,
   149                                          const StringPiece& s,
   150                                          StringPiece::size_type pos) {
   151   if (self.size() == 0)
   152     return StringPiece::npos;
   154   if (s.size() == 0)
   155     return 0;
   157   // Avoid the cost of BuildLookupTable() for a single-character search.
   158   if (s.size() == 1)
   159     return find_first_not_of(self, s.data()[0], pos);
   161   bool lookup[UCHAR_MAX + 1] = { false };
   162   BuildLookupTable(s, lookup);
   163   for (StringPiece::size_type i = pos; i < self.size(); ++i) {
   164     if (!lookup[static_cast<unsigned char>(self.data()[i])]) {
   165       return i;
   166     }
   167   }
   168   return StringPiece::npos;
   169 }
   171 StringPiece::size_type find_first_not_of(const StringPiece& self,
   172                                          char c,
   173                                          StringPiece::size_type pos) {
   174   if (self.size() == 0)
   175     return StringPiece::npos;
   177   for (; pos < self.size(); ++pos) {
   178     if (self.data()[pos] != c) {
   179       return pos;
   180     }
   181   }
   182   return StringPiece::npos;
   183 }
   185 StringPiece::size_type find_last_of(const StringPiece& self,
   186                                     const StringPiece& s,
   187                                     StringPiece::size_type pos) {
   188   if (self.size() == 0 || s.size() == 0)
   189     return StringPiece::npos;
   191   // Avoid the cost of BuildLookupTable() for a single-character search.
   192   if (s.size() == 1)
   193     return rfind(self, s.data()[0], pos);
   195   bool lookup[UCHAR_MAX + 1] = { false };
   196   BuildLookupTable(s, lookup);
   197   for (StringPiece::size_type i = std::min(pos, self.size() - 1); ; --i) {
   198     if (lookup[static_cast<unsigned char>(self.data()[i])])
   199       return i;
   200     if (i == 0)
   201       break;
   202   }
   203   return StringPiece::npos;
   204 }
   206 StringPiece::size_type find_last_not_of(const StringPiece& self,
   207                                         const StringPiece& s,
   208                                         StringPiece::size_type pos) {
   209   if (self.size() == 0)
   210     return StringPiece::npos;
   212   StringPiece::size_type i = std::min(pos, self.size() - 1);
   213   if (s.size() == 0)
   214     return i;
   216   // Avoid the cost of BuildLookupTable() for a single-character search.
   217   if (s.size() == 1)
   218     return find_last_not_of(self, s.data()[0], pos);
   220   bool lookup[UCHAR_MAX + 1] = { false };
   221   BuildLookupTable(s, lookup);
   222   for (; ; --i) {
   223     if (!lookup[static_cast<unsigned char>(self.data()[i])])
   224       return i;
   225     if (i == 0)
   226       break;
   227   }
   228   return StringPiece::npos;
   229 }
   231 StringPiece::size_type find_last_not_of(const StringPiece& self,
   232                                         char c,
   233                                         StringPiece::size_type pos) {
   234   if (self.size() == 0)
   235     return StringPiece::npos;
   237   for (StringPiece::size_type i = std::min(pos, self.size() - 1); ; --i) {
   238     if (self.data()[i] != c)
   239       return i;
   240     if (i == 0)
   241       break;
   242   }
   243   return StringPiece::npos;
   244 }
   246 StringPiece substr(const StringPiece& self,
   247                    StringPiece::size_type pos,
   248                    StringPiece::size_type n) {
   249   if (pos > self.size()) pos = self.size();
   250   if (n > self.size() - pos) n = self.size() - pos;
   251   return StringPiece(self.data() + pos, n);
   252 }
   254 }  // namespace internal
   255 }  // namespace base

mercurial