1 //
2 // Copyright 2012 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6
7 #include "PreprocessorTest.h"
8 #include "compiler/preprocessor/Token.h"
9
10 namespace angle
11 {
12
13 class ExtensionTest : public SimplePreprocessorTest
14 {};
15
TEST_F(ExtensionTest,Valid)16 TEST_F(ExtensionTest, Valid)
17 {
18 const char *str = "#extension foo : bar\n";
19 const char *expected = "\n";
20
21 using testing::_;
22 EXPECT_CALL(mDirectiveHandler, handleExtension(pp::SourceLocation(0, 1), "foo", "bar"));
23 // No error or warning.
24 EXPECT_CALL(mDiagnostics, print(_, _, _)).Times(0);
25
26 preprocess(str, expected);
27 }
28
TEST_F(ExtensionTest,Comments)29 TEST_F(ExtensionTest, Comments)
30 {
31 const char *str =
32 "/*foo*/"
33 "#"
34 "/*foo*/"
35 "extension"
36 "/*foo*/"
37 "foo"
38 "/*foo*/"
39 ":"
40 "/*foo*/"
41 "bar"
42 "/*foo*/"
43 "//foo"
44 "\n";
45 const char *expected = "\n";
46
47 using testing::_;
48 EXPECT_CALL(mDirectiveHandler, handleExtension(pp::SourceLocation(0, 1), "foo", "bar"));
49 // No error or warning.
50 EXPECT_CALL(mDiagnostics, print(_, _, _)).Times(0);
51
52 preprocess(str, expected);
53 }
54
TEST_F(ExtensionTest,MissingNewline)55 TEST_F(ExtensionTest, MissingNewline)
56 {
57 const char *str = "#extension foo : bar";
58 const char *expected = "";
59
60 using testing::_;
61 // Directive successfully parsed.
62 EXPECT_CALL(mDirectiveHandler, handleExtension(pp::SourceLocation(0, 1), "foo", "bar"));
63 // Error reported about EOF.
64 EXPECT_CALL(mDiagnostics, print(pp::Diagnostics::PP_EOF_IN_DIRECTIVE, _, _));
65
66 preprocess(str, expected);
67 }
68
TEST_F(ExtensionTest,ExtensionAfterNonPreProcessorTokenESSL1)69 TEST_F(ExtensionTest, ExtensionAfterNonPreProcessorTokenESSL1)
70 {
71 const char *str =
72 "int baz = 1;\n"
73 "#extension foo : bar\n";
74 const char *expected = "int baz = 1;\n\n";
75
76 using testing::_;
77 #if defined(ANGLE_PLATFORM_CHROMEOS)
78 // Directive successfully parsed.
79 EXPECT_CALL(mDirectiveHandler, handleExtension(pp::SourceLocation(0, 2), "foo", "bar"));
80 #endif
81 // Expect an error (chromeos warning) about extension pragmas after non-preprocessor tokens.
82 EXPECT_CALL(mDiagnostics, print(pp::Diagnostics::PP_NON_PP_TOKEN_BEFORE_EXTENSION_ESSL1, _, _));
83
84 preprocess(str, expected);
85 }
86
TEST_F(ExtensionTest,ExtensionAfterNonPreProcessorTokenESSL3)87 TEST_F(ExtensionTest, ExtensionAfterNonPreProcessorTokenESSL3)
88 {
89 const char *str =
90 "#version 300 es\n"
91 "int baz = 1;\n"
92 "#extension foo : bar\n";
93 const char *expected = "\nint baz = 1;\n\n";
94
95 using testing::_;
96 // Directive successfully parsed.
97 EXPECT_CALL(mDirectiveHandler, handleVersion(pp::SourceLocation(0, 1), 300, SH_GLES2_SPEC));
98 // Expect an error about extension pragmas after non-preprocessor tokens.
99 EXPECT_CALL(mDiagnostics, print(pp::Diagnostics::PP_NON_PP_TOKEN_BEFORE_EXTENSION_ESSL3, _, _));
100
101 preprocess(str, expected);
102 }
103
104 struct ExtensionTestParam
105 {
106 const char *str;
107 pp::Diagnostics::ID id;
108 };
109
110 using testing::WithParamInterface;
111 class InvalidExtensionTest : public ExtensionTest, public WithParamInterface<ExtensionTestParam>
112 {};
113
TEST_P(InvalidExtensionTest,Identified)114 TEST_P(InvalidExtensionTest, Identified)
115 {
116 ExtensionTestParam param = GetParam();
117 const char *expected = "\n";
118
119 using testing::_;
120 // No handleExtension call.
121 EXPECT_CALL(mDirectiveHandler, handleExtension(_, _, _)).Times(0);
122 // Invalid extension directive call.
123 EXPECT_CALL(mDiagnostics, print(param.id, pp::SourceLocation(0, 1), _));
124
125 preprocess(param.str, expected);
126 }
127
128 static const ExtensionTestParam kParams[] = {
129 {"#extension\n", pp::Diagnostics::PP_INVALID_EXTENSION_DIRECTIVE},
130 {"#extension 1\n", pp::Diagnostics::PP_INVALID_EXTENSION_NAME},
131 {"#extension foo bar\n", pp::Diagnostics::PP_UNEXPECTED_TOKEN},
132 {"#extension foo : \n", pp::Diagnostics::PP_INVALID_EXTENSION_DIRECTIVE},
133 {"#extension foo : 1\n", pp::Diagnostics::PP_INVALID_EXTENSION_BEHAVIOR},
134 {"#extension foo : bar baz\n", pp::Diagnostics::PP_UNEXPECTED_TOKEN}};
135 INSTANTIATE_TEST_SUITE_P(All, InvalidExtensionTest, testing::ValuesIn(kParams));
136
137 } // namespace angle
138