• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2016 PDFium 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 
5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6 
7 #include "core/fpdfdoc/cpdf_metadata.h"
8 
9 #include <memory>
10 
11 #include "core/fpdfapi/parser/cpdf_stream.h"
12 #include "core/fpdfapi/parser/cpdf_stream_acc.h"
13 #include "core/fxcrt/cfx_readonlymemorystream.h"
14 #include "core/fxcrt/fx_codepage.h"
15 #include "core/fxcrt/xml/cfx_xmldocument.h"
16 #include "core/fxcrt/xml/cfx_xmlelement.h"
17 #include "core/fxcrt/xml/cfx_xmlparser.h"
18 
19 namespace {
20 
CheckForSharedFormInternal(CFX_XMLElement * element,std::vector<UnsupportedFeature> * unsupported)21 void CheckForSharedFormInternal(CFX_XMLElement* element,
22                                 std::vector<UnsupportedFeature>* unsupported) {
23   WideString attr =
24       element->GetAttribute(WideString::FromASCII("xmlns:adhocwf"));
25   if (attr.EqualsASCII("http://ns.adobe.com/AcrobatAdhocWorkflow/1.0/")) {
26     for (const auto* child = element->GetFirstChild(); child;
27          child = child->GetNextSibling()) {
28       if (child->GetType() != CFX_XMLNode::Type::kElement)
29         continue;
30 
31       const auto* child_elem = static_cast<const CFX_XMLElement*>(child);
32       if (!child_elem->GetName().EqualsASCII("adhocwf:workflowType"))
33         continue;
34 
35       switch (child_elem->GetTextData().GetInteger()) {
36         case 0:
37           unsupported->push_back(UnsupportedFeature::kDocumentSharedFormEmail);
38           break;
39         case 1:
40           unsupported->push_back(
41               UnsupportedFeature::kDocumentSharedFormAcrobat);
42           break;
43         case 2:
44           unsupported->push_back(
45               UnsupportedFeature::kDocumentSharedFormFilesystem);
46           break;
47       }
48       // We only care about the first one we find.
49       break;
50     }
51   }
52 
53   for (auto* child = element->GetFirstChild(); child;
54        child = child->GetNextSibling()) {
55     CFX_XMLElement* pElement = ToXMLElement(child);
56     if (pElement)
57       CheckForSharedFormInternal(pElement, unsupported);
58   }
59 }
60 
61 }  // namespace
62 
CPDF_Metadata(const CPDF_Stream * pStream)63 CPDF_Metadata::CPDF_Metadata(const CPDF_Stream* pStream) : stream_(pStream) {
64   ASSERT(pStream);
65 }
66 
67 CPDF_Metadata::~CPDF_Metadata() = default;
68 
CheckForSharedForm() const69 std::vector<UnsupportedFeature> CPDF_Metadata::CheckForSharedForm() const {
70   auto pAcc = pdfium::MakeRetain<CPDF_StreamAcc>(stream_.Get());
71   pAcc->LoadAllDataFiltered();
72 
73   auto stream = pdfium::MakeRetain<CFX_ReadOnlyMemoryStream>(pAcc->GetSpan());
74   CFX_XMLParser parser(stream);
75   std::unique_ptr<CFX_XMLDocument> doc = parser.Parse();
76   if (!doc)
77     return {};
78 
79   std::vector<UnsupportedFeature> unsupported;
80   CheckForSharedFormInternal(doc->GetRoot(), &unsupported);
81   return unsupported;
82 }
83