| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2013 Google Inc. All rights reserved. | 2 * Copyright (C) 2013 Google Inc. All rights reserved. |
| 3 * | 3 * |
| 4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
| 5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
| 6 * met: | 6 * met: |
| 7 * | 7 * |
| 8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
| 9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
| 10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 56 if (!platformData->typeface()) { | 56 if (!platformData->typeface()) { |
| 57 DLOG(ERROR) | 57 DLOG(ERROR) |
| 58 << "Empty typeface() in FontPlatformData when accessing FontDataCache."; | 58 << "Empty typeface() in FontPlatformData when accessing FontDataCache."; |
| 59 return nullptr; | 59 return nullptr; |
| 60 } | 60 } |
| 61 | 61 |
| 62 Cache::iterator result = m_cache.find(platformData); | 62 Cache::iterator result = m_cache.find(platformData); |
| 63 if (result == m_cache.end()) { | 63 if (result == m_cache.end()) { |
| 64 std::pair<RefPtr<SimpleFontData>, unsigned> newValue( | 64 std::pair<RefPtr<SimpleFontData>, unsigned> newValue( |
| 65 SimpleFontData::create(*platformData), shouldRetain == Retain ? 1 : 0); | 65 SimpleFontData::create(*platformData), shouldRetain == Retain ? 1 : 0); |
| 66 // The new SimpleFontData takes a copy of the incoming FontPlatformData obje
ct. The incoming key may be | 66 // The new SimpleFontData takes a copy of the incoming FontPlatformData |
| 67 // temporary. So, for cache storage, take the address of the newly created F
ontPlatformData that is copied an | 67 // object. The incoming key may be temporary. So, for cache storage, take |
| 68 // owned by SimpleFontData. | 68 // the address of the newly created FontPlatformData that is copied an owned |
| 69 // by SimpleFontData. |
| 69 m_cache.set(&newValue.first->platformData(), newValue); | 70 m_cache.set(&newValue.first->platformData(), newValue); |
| 70 if (shouldRetain == DoNotRetain) | 71 if (shouldRetain == DoNotRetain) |
| 71 m_inactiveFontData.add(newValue.first); | 72 m_inactiveFontData.add(newValue.first); |
| 72 return newValue.first.release(); | 73 return newValue.first.release(); |
| 73 } | 74 } |
| 74 | 75 |
| 75 if (!result.get()->value.second) { | 76 if (!result.get()->value.second) { |
| 76 ASSERT(m_inactiveFontData.contains(result.get()->value.first)); | 77 ASSERT(m_inactiveFontData.contains(result.get()->value.first)); |
| 77 m_inactiveFontData.remove(result.get()->value.first); | 78 m_inactiveFontData.remove(result.get()->value.first); |
| 78 } | 79 } |
| 79 | 80 |
| 80 if (shouldRetain == Retain) { | 81 if (shouldRetain == Retain) { |
| 81 result.get()->value.second++; | 82 result.get()->value.second++; |
| 82 } else if (!result.get()->value.second) { | 83 } else if (!result.get()->value.second) { |
| 83 // If shouldRetain is DoNotRetain and count is 0, we want to remove the font
Data from | 84 // If shouldRetain is DoNotRetain and count is 0, we want to remove the |
| 84 // m_inactiveFontData (above) and re-add here to update LRU position. | 85 // fontData from m_inactiveFontData (above) and re-add here to update LRU |
| 86 // position. |
| 85 m_inactiveFontData.add(result.get()->value.first); | 87 m_inactiveFontData.add(result.get()->value.first); |
| 86 } | 88 } |
| 87 | 89 |
| 88 return result.get()->value.first; | 90 return result.get()->value.first; |
| 89 } | 91 } |
| 90 | 92 |
| 91 bool FontDataCache::contains(const FontPlatformData* fontPlatformData) const { | 93 bool FontDataCache::contains(const FontPlatformData* fontPlatformData) const { |
| 92 return m_cache.contains(fontPlatformData); | 94 return m_cache.contains(fontPlatformData); |
| 93 } | 95 } |
| 94 | 96 |
| (...skipping 26 matching lines...) Expand all Loading... |
| 121 return purgeLeastRecentlyUsed(INT_MAX); | 123 return purgeLeastRecentlyUsed(INT_MAX); |
| 122 | 124 |
| 123 if (m_inactiveFontData.size() > cMaxInactiveFontData) | 125 if (m_inactiveFontData.size() > cMaxInactiveFontData) |
| 124 return purgeLeastRecentlyUsed(m_inactiveFontData.size() - | 126 return purgeLeastRecentlyUsed(m_inactiveFontData.size() - |
| 125 cTargetInactiveFontData); | 127 cTargetInactiveFontData); |
| 126 | 128 |
| 127 return false; | 129 return false; |
| 128 } | 130 } |
| 129 | 131 |
| 130 bool FontDataCache::purgeLeastRecentlyUsed(int count) { | 132 bool FontDataCache::purgeLeastRecentlyUsed(int count) { |
| 131 static bool | 133 // Guard against reentry when e.g. a deleted FontData releases its small caps |
| 132 isPurging; // Guard against reentry when e.g. a deleted FontData releases
its small caps FontData. | 134 // FontData. |
| 135 static bool isPurging; |
| 133 if (isPurging) | 136 if (isPurging) |
| 134 return false; | 137 return false; |
| 135 | 138 |
| 136 isPurging = true; | 139 isPurging = true; |
| 137 | 140 |
| 138 Vector<RefPtr<SimpleFontData>, 20> fontDataToDelete; | 141 Vector<RefPtr<SimpleFontData>, 20> fontDataToDelete; |
| 139 ListHashSet<RefPtr<SimpleFontData>>::iterator end = m_inactiveFontData.end(); | 142 ListHashSet<RefPtr<SimpleFontData>>::iterator end = m_inactiveFontData.end(); |
| 140 ListHashSet<RefPtr<SimpleFontData>>::iterator it = m_inactiveFontData.begin(); | 143 ListHashSet<RefPtr<SimpleFontData>>::iterator it = m_inactiveFontData.begin(); |
| 141 for (int i = 0; i < count && it != end; ++it, ++i) { | 144 for (int i = 0; i < count && it != end; ++it, ++i) { |
| 142 RefPtr<SimpleFontData>& fontData = *it.get(); | 145 RefPtr<SimpleFontData>& fontData = *it.get(); |
| 143 m_cache.remove(&(fontData->platformData())); | 146 m_cache.remove(&(fontData->platformData())); |
| 144 // We should not delete SimpleFontData here because deletion can modify m_in
activeFontData. See http://trac.webkit.org/changeset/44011 | 147 // We should not delete SimpleFontData here because deletion can modify |
| 148 // m_inactiveFontData. See http://trac.webkit.org/changeset/44011 |
| 145 fontDataToDelete.append(fontData); | 149 fontDataToDelete.append(fontData); |
| 146 } | 150 } |
| 147 | 151 |
| 148 if (it == end) { | 152 if (it == end) { |
| 149 // Removed everything | 153 // Removed everything |
| 150 m_inactiveFontData.clear(); | 154 m_inactiveFontData.clear(); |
| 151 } else { | 155 } else { |
| 152 for (int i = 0; i < count; ++i) | 156 for (int i = 0; i < count; ++i) |
| 153 m_inactiveFontData.remove(m_inactiveFontData.begin()); | 157 m_inactiveFontData.remove(m_inactiveFontData.begin()); |
| 154 } | 158 } |
| 155 | 159 |
| 156 bool didWork = fontDataToDelete.size(); | 160 bool didWork = fontDataToDelete.size(); |
| 157 | 161 |
| 158 fontDataToDelete.clear(); | 162 fontDataToDelete.clear(); |
| 159 | 163 |
| 160 isPurging = false; | 164 isPurging = false; |
| 161 | 165 |
| 162 return didWork; | 166 return didWork; |
| 163 } | 167 } |
| 164 | 168 |
| 165 } // namespace blink | 169 } // namespace blink |
| OLD | NEW |