• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2016 The PDFium Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include <limits>
6 
7 #include "core/fpdfapi/parser/cpdf_object.h"
8 #include "core/fpdfapi/parser/cpdf_parser.h"
9 #include "core/fpdfapi/parser/cpdf_syntax_parser.h"
10 #include "core/fxcrt/cfx_read_only_span_stream.h"
11 #include "core/fxcrt/fx_extension.h"
12 #include "testing/gtest/include/gtest/gtest.h"
13 #include "testing/utils/path_service.h"
14 
TEST(SyntaxParserTest,ReadHexString)15 TEST(SyntaxParserTest, ReadHexString) {
16   {
17     // Empty string.
18     static const uint8_t data[] = "";
19     CPDF_SyntaxParser parser(
20         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 0)));
21     EXPECT_EQ("", parser.ReadHexString());
22     EXPECT_EQ(0, parser.GetPos());
23   }
24 
25   {
26     // Blank string.
27     static const uint8_t data[] = "  ";
28     CPDF_SyntaxParser parser(
29         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 2)));
30     EXPECT_EQ("", parser.ReadHexString());
31     EXPECT_EQ(2, parser.GetPos());
32   }
33 
34   {
35     // Skips unknown characters.
36     static const uint8_t data[] = "z12b";
37     CPDF_SyntaxParser parser(
38         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 4)));
39     EXPECT_EQ("\x12\xb0", parser.ReadHexString());
40     EXPECT_EQ(4, parser.GetPos());
41   }
42 
43   {
44     // Skips unknown characters.
45     static const uint8_t data[] = "*<&*#$^&@1";
46     CPDF_SyntaxParser parser(pdfium::MakeRetain<CFX_ReadOnlySpanStream>(
47         pdfium::make_span(data, 10)));
48     EXPECT_EQ("\x10", parser.ReadHexString());
49     EXPECT_EQ(10, parser.GetPos());
50   }
51 
52   {
53     // Skips unknown characters.
54     static const uint8_t data[] = "\x80zab";
55     CPDF_SyntaxParser parser(
56         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 4)));
57     EXPECT_EQ("\xab", parser.ReadHexString());
58     EXPECT_EQ(4, parser.GetPos());
59   }
60 
61   {
62     // Skips unknown characters.
63     static const uint8_t data[] = "\xffzab";
64     CPDF_SyntaxParser parser(
65         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 4)));
66     EXPECT_EQ("\xab", parser.ReadHexString());
67     EXPECT_EQ(4, parser.GetPos());
68   }
69 
70   {
71     // Regular conversion.
72     static const uint8_t data[] = "1A2b>abcd";
73     CPDF_SyntaxParser parser(
74         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 9)));
75     EXPECT_EQ("\x1a\x2b", parser.ReadHexString());
76     EXPECT_EQ(5, parser.GetPos());
77   }
78 
79   {
80     // Position out of bounds.
81     static const uint8_t data[] = "12ab>";
82     CPDF_SyntaxParser parser(
83         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 5)));
84     parser.SetPos(5);
85     EXPECT_EQ("", parser.ReadHexString());
86 
87     parser.SetPos(6);
88     EXPECT_EQ("", parser.ReadHexString());
89 
90     parser.SetPos(std::numeric_limits<FX_FILESIZE>::max());
91     EXPECT_EQ("", parser.ReadHexString());
92 
93     // Check string still parses when set to 0.
94     parser.SetPos(0);
95     EXPECT_EQ("\x12\xab", parser.ReadHexString());
96   }
97 
98   {
99     // Missing ending >.
100     static const uint8_t data[] = "1A2b";
101     CPDF_SyntaxParser parser(
102         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 4)));
103     EXPECT_EQ("\x1a\x2b", parser.ReadHexString());
104     EXPECT_EQ(4, parser.GetPos());
105   }
106 
107   {
108     // Missing ending >.
109     static const uint8_t data[] = "12abz";
110     CPDF_SyntaxParser parser(
111         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 5)));
112     EXPECT_EQ("\x12\xab", parser.ReadHexString());
113     EXPECT_EQ(5, parser.GetPos());
114   }
115 
116   {
117     // Uneven number of bytes.
118     static const uint8_t data[] = "1A2>asdf";
119     CPDF_SyntaxParser parser(
120         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 8)));
121     EXPECT_EQ("\x1a\x20", parser.ReadHexString());
122     EXPECT_EQ(4, parser.GetPos());
123   }
124 
125   {
126     // Uneven number of bytes.
127     static const uint8_t data[] = "1A2zasdf";
128     CPDF_SyntaxParser parser(
129         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 8)));
130     EXPECT_EQ("\x1a\x2a\xdf", parser.ReadHexString());
131     EXPECT_EQ(8, parser.GetPos());
132   }
133 
134   {
135     // Just ending character.
136     static const uint8_t data[] = ">";
137     CPDF_SyntaxParser parser(
138         pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 1)));
139     EXPECT_EQ("", parser.ReadHexString());
140     EXPECT_EQ(1, parser.GetPos());
141   }
142 }
143 
TEST(SyntaxParserTest,GetInvalidReference)144 TEST(SyntaxParserTest, GetInvalidReference) {
145   // Data with a reference with number CPDF_Object::kInvalidObjNum
146   static const uint8_t data[] = "4294967295 0 R";
147   CPDF_SyntaxParser parser(
148       pdfium::MakeRetain<CFX_ReadOnlySpanStream>(pdfium::make_span(data, 14)));
149   RetainPtr<CPDF_Object> ref = parser.GetObjectBody(nullptr);
150   EXPECT_FALSE(ref);
151 }
152 
TEST(SyntaxParserTest,PeekNextWord)153 TEST(SyntaxParserTest, PeekNextWord) {
154   static const uint8_t data[] = "    WORD ";
155   CPDF_SyntaxParser parser(pdfium::MakeRetain<CFX_ReadOnlySpanStream>(data));
156   EXPECT_EQ("WORD", parser.PeekNextWord());
157   EXPECT_EQ("WORD", parser.GetNextWord().word);
158 }
159