summaryrefslogtreecommitdiff
path: root/xfa/src/fde/css/fde_csscache.cpp
diff options
context:
space:
mode:
authorDan Sinclair <dsinclair@chromium.org>2016-03-09 15:33:14 -0500
committerDan Sinclair <dsinclair@chromium.org>2016-03-09 15:33:14 -0500
commit2e95951e06bd4d11459fb257c7c2b8fc881854e8 (patch)
tree742484ab5d944d9c2c930133cc5968d6c6a5678d /xfa/src/fde/css/fde_csscache.cpp
parentea2a252c40f95616eb0f03318222f0c32ef90eff (diff)
downloadpdfium-2e95951e06bd4d11459fb257c7c2b8fc881854e8.tar.xz
Cleanup the xfa/src/fdp directory.
This CL renames xfa/src/fdp to xfa/src/fde to better match all of the content (nothing mentions fdp other then the directory name). The inner src/ and include/ folders are collapsed up a level and xfa/src/fdp/src/fde is moved up to xfa/src/fde. Some of the header moves conflicted with existing headers. In that case, the existing header had the content moved into the .cpp file and we replaced the existing header with the one from include/. R=tsepez@chromium.org Review URL: https://codereview.chromium.org/1784543002 .
Diffstat (limited to 'xfa/src/fde/css/fde_csscache.cpp')
-rw-r--r--xfa/src/fde/css/fde_csscache.cpp149
1 files changed, 149 insertions, 0 deletions
diff --git a/xfa/src/fde/css/fde_csscache.cpp b/xfa/src/fde/css/fde_csscache.cpp
new file mode 100644
index 0000000000..3fee9f862f
--- /dev/null
+++ b/xfa/src/fde/css/fde_csscache.cpp
@@ -0,0 +1,149 @@
+// Copyright 2014 PDFium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
+
+#include "xfa/src/fde/css/fde_csscache.h"
+
+#include <algorithm>
+
+#include "core/include/fxcrt/fx_ext.h"
+
+FDE_CSSCACHEITEM::FDE_CSSCACHEITEM(IFDE_CSSStyleSheet* p)
+ : pStylesheet(p), dwActivity(0) {
+ FXSYS_assert(pStylesheet);
+ pStylesheet->AddRef();
+}
+FDE_CSSCACHEITEM::~FDE_CSSCACHEITEM() {
+ pStylesheet->Release();
+}
+IFDE_CSSStyleSheetCache* IFDE_CSSStyleSheetCache::Create() {
+ return new CFDE_CSSStyleSheetCache;
+}
+
+CFDE_CSSStyleSheetCache::CFDE_CSSStyleSheetCache()
+ : m_pFixedStore(NULL), m_iMaxItems(5) {}
+
+CFDE_CSSStyleSheetCache::~CFDE_CSSStyleSheetCache() {
+ for (const auto& pair : m_Stylesheets) {
+ FXTARGET_DeleteWith(FDE_CSSCACHEITEM, m_pFixedStore, pair.second);
+ }
+ m_Stylesheets.clear();
+ if (m_pFixedStore) {
+ m_pFixedStore->Release();
+ }
+}
+void CFDE_CSSStyleSheetCache::AddStyleSheet(const CFX_ByteStringC& szKey,
+ IFDE_CSSStyleSheet* pStyleSheet) {
+ FXSYS_assert(pStyleSheet != NULL);
+ if (m_pFixedStore == NULL) {
+ m_pFixedStore =
+ FX_CreateAllocator(FX_ALLOCTYPE_Fixed, std::max(10, m_iMaxItems),
+ sizeof(FDE_CSSCACHEITEM));
+ FXSYS_assert(m_pFixedStore != NULL);
+ }
+ auto it = m_Stylesheets.find(szKey);
+ if (it != m_Stylesheets.end()) {
+ FDE_CSSCACHEITEM* pItem = it->second;
+ if (pItem->pStylesheet != pStyleSheet) {
+ pItem->pStylesheet->Release();
+ pItem->pStylesheet = pStyleSheet;
+ pItem->pStylesheet->AddRef();
+ pItem->dwActivity = 0;
+ }
+ } else {
+ while (static_cast<int32_t>(m_Stylesheets.size()) >= m_iMaxItems) {
+ RemoveLowestActivityItem();
+ }
+ m_Stylesheets[szKey] =
+ FXTARGET_NewWith(m_pFixedStore) FDE_CSSCACHEITEM(pStyleSheet);
+ }
+}
+IFDE_CSSStyleSheet* CFDE_CSSStyleSheetCache::GetStyleSheet(
+ const CFX_ByteStringC& szKey) const {
+ auto it = m_Stylesheets.find(szKey);
+ if (it == m_Stylesheets.end()) {
+ return nullptr;
+ }
+ FDE_CSSCACHEITEM* pItem = it->second;
+ pItem->dwActivity++;
+ pItem->pStylesheet->AddRef();
+ return pItem->pStylesheet;
+}
+void CFDE_CSSStyleSheetCache::RemoveStyleSheet(const CFX_ByteStringC& szKey) {
+ auto it = m_Stylesheets.find(szKey);
+ if (it == m_Stylesheets.end()) {
+ return;
+ }
+ FXTARGET_DeleteWith(FDE_CSSCACHEITEM, m_pFixedStore, it->second);
+ m_Stylesheets.erase(it);
+}
+void CFDE_CSSStyleSheetCache::RemoveLowestActivityItem() {
+ auto found = m_Stylesheets.end();
+ for (auto it = m_Stylesheets.begin(); it != m_Stylesheets.end(); ++it) {
+ switch (it->first.GetID()) {
+ case FXBSTR_ID('#', 'U', 'S', 'E'):
+ case FXBSTR_ID('#', 'A', 'G', 'E'):
+ continue;
+ }
+ if (found == m_Stylesheets.end() ||
+ it->second->dwActivity > found->second->dwActivity) {
+ found = it;
+ }
+ }
+ if (found != m_Stylesheets.end()) {
+ FXTARGET_DeleteWith(FDE_CSSCACHEITEM, m_pFixedStore, found->second);
+ m_Stylesheets.erase(found);
+ }
+}
+FDE_CSSTAGCACHE::FDE_CSSTAGCACHE(FDE_CSSTAGCACHE* parent,
+ IFDE_CSSTagProvider* tag)
+ : pTag(tag),
+ pParent(parent),
+ dwIDHash(0),
+ dwTagHash(0),
+ iClassIndex(0),
+ dwClassHashs(1) {
+ FXSYS_assert(pTag != NULL);
+ CFX_WideStringC wsValue, wsName = pTag->GetTagName();
+ dwTagHash =
+ FX_HashCode_String_GetW(wsName.GetPtr(), wsName.GetLength(), TRUE);
+ FX_POSITION pos = pTag->GetFirstAttribute();
+ while (pos != NULL) {
+ pTag->GetNextAttribute(pos, wsName, wsValue);
+ FX_DWORD dwNameHash =
+ FX_HashCode_String_GetW(wsName.GetPtr(), wsName.GetLength(), TRUE);
+ static const FX_DWORD s_dwIDHash = FX_HashCode_String_GetW(L"id", 2, TRUE);
+ static const FX_DWORD s_dwClassHash =
+ FX_HashCode_String_GetW(L"class", 5, TRUE);
+ if (dwNameHash == s_dwClassHash) {
+ FX_DWORD dwHash =
+ FX_HashCode_String_GetW(wsValue.GetPtr(), wsValue.GetLength());
+ dwClassHashs.Add(dwHash);
+ } else if (dwNameHash == s_dwIDHash) {
+ dwIDHash = FX_HashCode_String_GetW(wsValue.GetPtr(), wsValue.GetLength());
+ }
+ }
+}
+FDE_CSSTAGCACHE::FDE_CSSTAGCACHE(const FDE_CSSTAGCACHE& it)
+ : pTag(it.pTag),
+ pParent(it.pParent),
+ dwIDHash(it.dwIDHash),
+ dwTagHash(it.dwTagHash),
+ iClassIndex(0),
+ dwClassHashs(1) {
+ if (it.dwClassHashs.GetSize() > 0) {
+ dwClassHashs.Copy(it.dwClassHashs);
+ }
+}
+void CFDE_CSSAccelerator::OnEnterTag(IFDE_CSSTagProvider* pTag) {
+ FDE_CSSTAGCACHE* pTop = GetTopElement();
+ FDE_CSSTAGCACHE item(pTop, pTag);
+ m_Stack.Push(item);
+}
+void CFDE_CSSAccelerator::OnLeaveTag(IFDE_CSSTagProvider* pTag) {
+ FXSYS_assert(m_Stack.GetTopElement());
+ FXSYS_assert(m_Stack.GetTopElement()->GetTag() == pTag);
+ m_Stack.Pop();
+}