1 | /* |
2 | * Copyright 2014 Google Inc. All rights reserved. |
3 | * |
4 | * Licensed under the Apache License, Version 2.0 (the "License"); |
5 | * you may not use this file except in compliance with the License. |
6 | * You may obtain a copy of the License at |
7 | * |
8 | * http://www.apache.org/licenses/LICENSE-2.0 |
9 | * |
10 | * Unless required by applicable law or agreed to in writing, software |
11 | * distributed under the License is distributed on an "AS IS" BASIS, |
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
13 | * See the License for the specific language governing permissions and |
14 | * limitations under the License. |
15 | */ |
16 | |
17 | #ifndef FLATBUFFERS_CODE_GENERATORS_H_ |
18 | #define FLATBUFFERS_CODE_GENERATORS_H_ |
19 | |
20 | #include <map> |
21 | #include <sstream> |
22 | #include "flatbuffers/idl.h" |
23 | |
24 | namespace flatbuffers { |
25 | |
26 | // Utility class to assist in generating code through use of text templates. |
27 | // |
28 | // Example code: |
29 | // CodeWriter code; |
30 | // code.SetValue("NAME", "Foo"); |
31 | // code += "void {{NAME}}() { printf("%s", "{{NAME}}"); }"; |
32 | // code.SetValue("NAME", "Bar"); |
33 | // code += "void {{NAME}}() { printf("%s", "{{NAME}}"); }"; |
34 | // std::cout << code.ToString() << std::endl; |
35 | // |
36 | // Output: |
37 | // void Foo() { printf("%s", "Foo"); } |
38 | // void Bar() { printf("%s", "Bar"); } |
39 | class CodeWriter { |
40 | public: |
41 | CodeWriter() {} |
42 | |
43 | // Clears the current "written" code. |
44 | void Clear() { |
45 | stream_.str("" ); |
46 | stream_.clear(); |
47 | } |
48 | |
49 | // Associates a key with a value. All subsequent calls to operator+=, where |
50 | // the specified key is contained in {{ and }} delimiters will be replaced by |
51 | // the given value. |
52 | void SetValue(const std::string &key, const std::string &value) { |
53 | value_map_[key] = value; |
54 | } |
55 | |
56 | // Appends the given text to the generated code as well as a newline |
57 | // character. Any text within {{ and }} delimeters is replaced by values |
58 | // previously stored in the CodeWriter by calling SetValue above. The newline |
59 | // will be suppressed if the text ends with the \\ character. |
60 | void operator+=(std::string text); |
61 | |
62 | // Returns the current contents of the CodeWriter as a std::string. |
63 | std::string ToString() const { return stream_.str(); } |
64 | |
65 | private: |
66 | std::map<std::string, std::string> value_map_; |
67 | std::stringstream stream_; |
68 | }; |
69 | |
70 | class BaseGenerator { |
71 | public: |
72 | virtual bool generate() = 0; |
73 | |
74 | static std::string NamespaceDir(const Parser &parser, const std::string &path, |
75 | const Namespace &ns); |
76 | |
77 | protected: |
78 | BaseGenerator(const Parser &parser, const std::string &path, |
79 | const std::string &file_name, |
80 | const std::string qualifying_start, |
81 | const std::string qualifying_separator) |
82 | : parser_(parser), |
83 | path_(path), |
84 | file_name_(file_name), |
85 | qualifying_start_(qualifying_start), |
86 | qualifying_separator_(qualifying_separator) {} |
87 | virtual ~BaseGenerator() {} |
88 | |
89 | // No copy/assign. |
90 | BaseGenerator &operator=(const BaseGenerator &); |
91 | BaseGenerator(const BaseGenerator &); |
92 | |
93 | std::string NamespaceDir(const Namespace &ns) const; |
94 | |
95 | static const char *FlatBuffersGeneratedWarning(); |
96 | |
97 | static std::string FullNamespace(const char *separator, const Namespace &ns); |
98 | |
99 | static std::string LastNamespacePart(const Namespace &ns); |
100 | |
101 | // tracks the current namespace for early exit in WrapInNameSpace |
102 | // c++, java and csharp returns a different namespace from |
103 | // the following default (no early exit, always fully qualify), |
104 | // which works for js and php |
105 | virtual const Namespace *CurrentNameSpace() const { return nullptr; } |
106 | |
107 | // Ensure that a type is prefixed with its namespace whenever it is used |
108 | // outside of its namespace. |
109 | std::string WrapInNameSpace(const Namespace *ns, |
110 | const std::string &name) const; |
111 | |
112 | std::string WrapInNameSpace(const Definition &def) const; |
113 | |
114 | std::string GetNameSpace(const Definition &def) const; |
115 | |
116 | const Parser &parser_; |
117 | const std::string &path_; |
118 | const std::string &file_name_; |
119 | const std::string qualifying_start_; |
120 | const std::string qualifying_separator_; |
121 | }; |
122 | |
123 | struct { |
124 | const char *; |
125 | const char *; |
126 | const char *; |
127 | }; |
128 | |
129 | extern void (const std::vector<std::string> &dc, |
130 | std::string *code_ptr, const CommentConfig *config, |
131 | const char *prefix = "" ); |
132 | |
133 | class FloatConstantGenerator { |
134 | public: |
135 | virtual ~FloatConstantGenerator() {} |
136 | std::string GenFloatConstant(const FieldDef &field) const; |
137 | |
138 | private: |
139 | virtual std::string Value(double v, const std::string &src) const = 0; |
140 | virtual std::string Inf(double v) const = 0; |
141 | virtual std::string NaN(double v) const = 0; |
142 | |
143 | virtual std::string Value(float v, const std::string &src) const = 0; |
144 | virtual std::string Inf(float v) const = 0; |
145 | virtual std::string NaN(float v) const = 0; |
146 | |
147 | template<typename T> |
148 | std::string GenFloatConstantImpl(const FieldDef &field) const; |
149 | }; |
150 | |
151 | class SimpleFloatConstantGenerator : public FloatConstantGenerator { |
152 | public: |
153 | SimpleFloatConstantGenerator(const char *nan_number, |
154 | const char *pos_inf_number, |
155 | const char *neg_inf_number); |
156 | |
157 | private: |
158 | std::string Value(double v, |
159 | const std::string &src) const FLATBUFFERS_OVERRIDE; |
160 | std::string Inf(double v) const FLATBUFFERS_OVERRIDE; |
161 | std::string NaN(double v) const FLATBUFFERS_OVERRIDE; |
162 | |
163 | std::string Value(float v, const std::string &src) const FLATBUFFERS_OVERRIDE; |
164 | std::string Inf(float v) const FLATBUFFERS_OVERRIDE; |
165 | std::string NaN(float v) const FLATBUFFERS_OVERRIDE; |
166 | |
167 | const std::string nan_number_; |
168 | const std::string pos_inf_number_; |
169 | const std::string neg_inf_number_; |
170 | }; |
171 | |
172 | // C++, C#, Java like generator. |
173 | class TypedFloatConstantGenerator : public FloatConstantGenerator { |
174 | public: |
175 | TypedFloatConstantGenerator(const char *double_prefix, |
176 | const char *single_prefix, const char *nan_number, |
177 | const char *pos_inf_number, |
178 | const char *neg_inf_number = "" ); |
179 | |
180 | private: |
181 | std::string Value(double v, |
182 | const std::string &src) const FLATBUFFERS_OVERRIDE; |
183 | std::string Inf(double v) const FLATBUFFERS_OVERRIDE; |
184 | |
185 | std::string NaN(double v) const FLATBUFFERS_OVERRIDE; |
186 | |
187 | std::string Value(float v, const std::string &src) const FLATBUFFERS_OVERRIDE; |
188 | std::string Inf(float v) const FLATBUFFERS_OVERRIDE; |
189 | std::string NaN(float v) const FLATBUFFERS_OVERRIDE; |
190 | |
191 | std::string MakeNaN(const std::string &prefix) const; |
192 | std::string MakeInf(bool neg, const std::string &prefix) const; |
193 | |
194 | const std::string double_prefix_; |
195 | const std::string single_prefix_; |
196 | const std::string nan_number_; |
197 | const std::string pos_inf_number_; |
198 | const std::string neg_inf_number_; |
199 | }; |
200 | |
201 | } // namespace flatbuffers |
202 | |
203 | #endif // FLATBUFFERS_CODE_GENERATORS_H_ |
204 | |