Chromium Code Reviews| Index: third_party/WebKit/Source/platform/wtf/text/StringImpl.cpp |
| diff --git a/third_party/WebKit/Source/platform/wtf/text/StringImpl.cpp b/third_party/WebKit/Source/platform/wtf/text/StringImpl.cpp |
| index a9e61cbbd96e36e82527c2296ad646322fe0954b..595bc04296ef7bd5741dafb35bd525954e864db4 100644 |
| --- a/third_party/WebKit/Source/platform/wtf/text/StringImpl.cpp |
| +++ b/third_party/WebKit/Source/platform/wtf/text/StringImpl.cpp |
| @@ -41,15 +41,6 @@ |
| #include <algorithm> |
| #include <memory> |
| -#ifdef STRING_STATS |
| -#include "platform/wtf/DataLog.h" |
| -#include "platform/wtf/HashMap.h" |
| -#include "platform/wtf/HashSet.h" |
| -#include "platform/wtf/RefCounted.h" |
| -#include "platform/wtf/ThreadingPrimitives.h" |
| -#include <unistd.h> |
| -#endif |
| - |
| using namespace std; |
| namespace WTF { |
| @@ -67,231 +58,6 @@ static_assert(sizeof(StringImpl) <= 3 * sizeof(int), |
| "StringImpl should stay small"); |
| #endif |
| -#ifdef STRING_STATS |
|
dcheng
2017/05/03 19:44:40
Hmm... FWIW, the last time I asked about removing
|
| - |
| -static Mutex& statsMutex() { |
| - DEFINE_STATIC_LOCAL(Mutex, mutex, ()); |
| - return mutex; |
| -} |
| - |
| -static HashSet<void*>& liveStrings() { |
| - // Notice that we can't use HashSet<StringImpl*> because then HashSet would |
| - // dedup identical strings. |
| - DEFINE_STATIC_LOCAL(HashSet<void*>, strings, ()); |
| - return strings; |
| -} |
| - |
| -void addStringForStats(StringImpl* string) { |
| - MutexLocker locker(statsMutex()); |
| - liveStrings().add(string); |
| -} |
| - |
| -void removeStringForStats(StringImpl* string) { |
| - MutexLocker locker(statsMutex()); |
| - liveStrings().remove(string); |
| -} |
| - |
| -static void fillWithSnippet(const StringImpl* string, Vector<char>& snippet) { |
| - const unsigned kMaxSnippetLength = 64; |
| - snippet.clear(); |
| - |
| - size_t expectedLength = std::min(string->length(), kMaxSnippetLength); |
| - if (expectedLength == kMaxSnippetLength) |
| - expectedLength += 3; // For the "...". |
| - ++expectedLength; // For the terminating '\0'. |
| - snippet.reserveCapacity(expectedLength); |
| - |
| - size_t i; |
| - for (i = 0; i < string->length() && i < kMaxSnippetLength; ++i) { |
| - UChar c = (*string)[i]; |
| - if (IsASCIIPrintable(c)) |
| - snippet.append(c); |
| - else |
| - snippet.append('?'); |
| - } |
| - if (i < string->length()) { |
| - snippet.append('.'); |
| - snippet.append('.'); |
| - snippet.append('.'); |
| - } |
| - snippet.append('\0'); |
| -} |
| - |
| -static bool isUnnecessarilyWide(const StringImpl* string) { |
| - if (string->is8Bit()) |
| - return false; |
| - UChar c = 0; |
| - for (unsigned i = 0; i < string->length(); ++i) |
| - c |= (*string)[i] >> 8; |
| - return !c; |
| -} |
| - |
| -class PerStringStats : public RefCounted<PerStringStats> { |
| - public: |
| - static PassRefPtr<PerStringStats> create() { |
| - return adoptRef(new PerStringStats); |
| - } |
| - |
| - void add(const StringImpl* string) { |
| - ++m_numberOfCopies; |
| - if (!m_length) { |
| - m_length = string->length(); |
| - fillWithSnippet(string, m_snippet); |
| - } |
| - if (string->isAtomic()) |
| - ++m_numberOfAtomicCopies; |
| - if (isUnnecessarilyWide(string)) |
| - m_unnecessarilyWide = true; |
| - } |
| - |
| - size_t totalCharacters() const { return m_numberOfCopies * m_length; } |
| - |
| - void print() { |
| - const char* status = "ok"; |
| - if (m_unnecessarilyWide) |
| - status = "16"; |
| - dataLogF("%8u copies (%s) of length %8u %s\n", m_numberOfCopies, status, |
| - m_length, m_snippet.data()); |
| - } |
| - |
| - bool m_unnecessarilyWide; |
| - unsigned m_numberOfCopies; |
| - unsigned m_length; |
| - unsigned m_numberOfAtomicCopies; |
| - Vector<char> m_snippet; |
| - |
| - private: |
| - PerStringStats() |
| - : m_unnecessarilyWide(false), |
| - m_numberOfCopies(0), |
| - m_length(0), |
| - m_numberOfAtomicCopies(0) {} |
| -}; |
| - |
| -bool operator<(const RefPtr<PerStringStats>& a, |
| - const RefPtr<PerStringStats>& b) { |
| - if (a->m_unnecessarilyWide != b->m_unnecessarilyWide) |
| - return !a->m_unnecessarilyWide && b->m_unnecessarilyWide; |
| - if (a->totalCharacters() != b->totalCharacters()) |
| - return a->totalCharacters() < b->totalCharacters(); |
| - if (a->m_numberOfCopies != b->m_numberOfCopies) |
| - return a->m_numberOfCopies < b->m_numberOfCopies; |
| - if (a->m_length != b->m_length) |
| - return a->m_length < b->m_length; |
| - return a->m_numberOfAtomicCopies < b->m_numberOfAtomicCopies; |
| -} |
| - |
| -static void printLiveStringStats(void*) { |
| - MutexLocker locker(statsMutex()); |
| - HashSet<void*>& strings = liveStrings(); |
| - |
| - HashMap<StringImpl*, RefPtr<PerStringStats>> stats; |
| - for (HashSet<void*>::iterator iter = strings.begin(); iter != strings.end(); |
| - ++iter) { |
| - StringImpl* string = static_cast<StringImpl*>(*iter); |
| - HashMap<StringImpl*, RefPtr<PerStringStats>>::iterator entry = |
| - stats.find(string); |
| - RefPtr<PerStringStats> value = |
| - entry == stats.end() ? RefPtr<PerStringStats>(PerStringStats::create()) |
| - : entry->value; |
| - value->add(string); |
| - stats.set(string, value.release()); |
| - } |
| - |
| - Vector<RefPtr<PerStringStats>> all; |
| - for (HashMap<StringImpl*, RefPtr<PerStringStats>>::iterator iter = |
| - stats.begin(); |
| - iter != stats.end(); ++iter) |
| - all.append(iter->value); |
| - |
| - std::sort(all.begin(), all.end()); |
| - std::reverse(all.begin(), all.end()); |
| - for (size_t i = 0; i < 20 && i < all.size(); ++i) |
| - all[i]->print(); |
| -} |
| - |
| -StringStats StringImpl::m_stringStats; |
| - |
| -unsigned StringStats::s_stringRemovesTillPrintStats = |
| - StringStats::s_printStringStatsFrequency; |
| - |
| -void StringStats::removeString(StringImpl* string) { |
| - unsigned length = string->length(); |
| - --m_totalNumberStrings; |
| - |
| - if (string->is8Bit()) { |
| - --m_number8BitStrings; |
| - m_total8BitData -= length; |
| - } else { |
| - --m_number16BitStrings; |
| - m_total16BitData -= length; |
| - } |
| - |
| - if (!--s_stringRemovesTillPrintStats) { |
| - s_stringRemovesTillPrintStats = s_printStringStatsFrequency; |
| - printStats(); |
| - } |
| -} |
| - |
| -void StringStats::printStats() { |
| - dataLogF("String stats for process id %d:\n", getpid()); |
| - |
| - unsigned long long totalNumberCharacters = m_total8BitData + m_total16BitData; |
| - double percent8Bit = |
| - m_totalNumberStrings |
| - ? ((double)m_number8BitStrings * 100) / (double)m_totalNumberStrings |
| - : 0.0; |
| - double average8bitLength = |
| - m_number8BitStrings |
| - ? (double)m_total8BitData / (double)m_number8BitStrings |
| - : 0.0; |
| - dataLogF( |
| - "%8u (%5.2f%%) 8 bit %12llu chars %12llu bytes avg length " |
| - "%6.1f\n", |
| - m_number8BitStrings, percent8Bit, m_total8BitData, m_total8BitData, |
| - average8bitLength); |
| - |
| - double percent16Bit = |
| - m_totalNumberStrings |
| - ? ((double)m_number16BitStrings * 100) / (double)m_totalNumberStrings |
| - : 0.0; |
| - double average16bitLength = |
| - m_number16BitStrings |
| - ? (double)m_total16BitData / (double)m_number16BitStrings |
| - : 0.0; |
| - dataLogF( |
| - "%8u (%5.2f%%) 16 bit %12llu chars %12llu bytes avg length " |
| - "%6.1f\n", |
| - m_number16BitStrings, percent16Bit, m_total16BitData, |
| - m_total16BitData * 2, average16bitLength); |
| - |
| - double averageLength = |
| - m_totalNumberStrings |
| - ? (double)totalNumberCharacters / (double)m_totalNumberStrings |
| - : 0.0; |
| - unsigned long long totalDataBytes = m_total8BitData + m_total16BitData * 2; |
| - dataLogF( |
| - "%8u Total %12llu chars %12llu bytes avg length " |
| - "%6.1f\n", |
| - m_totalNumberStrings, totalNumberCharacters, totalDataBytes, |
| - averageLength); |
| - unsigned long long totalSavedBytes = m_total8BitData; |
| - double percentSavings = totalSavedBytes |
| - ? ((double)totalSavedBytes * 100) / |
| - (double)(totalDataBytes + totalSavedBytes) |
| - : 0.0; |
| - dataLogF(" Total savings %12llu bytes (%5.2f%%)\n", totalSavedBytes, |
| - percentSavings); |
| - |
| - unsigned totalOverhead = m_totalNumberStrings * sizeof(StringImpl); |
| - double overheadPercent = (double)totalOverhead / (double)totalDataBytes * 100; |
| - dataLogF(" StringImpl overheader: %8u (%5.2f%%)\n", totalOverhead, |
| - overheadPercent); |
| - |
| - internal::callOnMainThread(&printLiveStringStats, nullptr); |
| -} |
| -#endif |
| - |
| void* StringImpl::operator new(size_t size) { |
| DCHECK_EQ(size, sizeof(StringImpl)); |
| return Partitions::BufferMalloc(size, "WTF::StringImpl"); |
| @@ -304,8 +70,6 @@ void StringImpl::operator delete(void* ptr) { |
| inline StringImpl::~StringImpl() { |
| DCHECK(!IsStatic()); |
| - STRING_STATS_REMOVE_STRING(this); |
| - |
| if (IsAtomic()) |
| AtomicStringTable::Instance().Remove(this); |
| } |