Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(43)

Side by Side Diff: build/android/gyp/java_cpp_enum.py

Issue 841173006: Add multi-line directives in the C++->Java enum generator. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: make multi-line syntax unambiguous Created 5 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | build/android/gyp/java_cpp_enum_tests.py » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 #!/usr/bin/env python 1 #!/usr/bin/env python
2 # 2 #
3 # Copyright 2014 The Chromium Authors. All rights reserved. 3 # Copyright 2014 The Chromium Authors. All rights reserved.
4 # Use of this source code is governed by a BSD-style license that can be 4 # Use of this source code is governed by a BSD-style license that can be
5 # found in the LICENSE file. 5 # found in the LICENSE file.
6 6
7 import collections 7 import collections
8 import re 8 import re
9 import optparse 9 import optparse
10 import os 10 import os
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after
117 DirectiveSet.prefix_to_strip_key) 117 DirectiveSet.prefix_to_strip_key)
118 118
119 119
120 class HeaderParser(object): 120 class HeaderParser(object):
121 single_line_comment_re = re.compile(r'\s*//') 121 single_line_comment_re = re.compile(r'\s*//')
122 multi_line_comment_start_re = re.compile(r'\s*/\*') 122 multi_line_comment_start_re = re.compile(r'\s*/\*')
123 enum_line_re = re.compile(r'^\s*(\w+)(\s*\=\s*([^,\n]+))?,?') 123 enum_line_re = re.compile(r'^\s*(\w+)(\s*\=\s*([^,\n]+))?,?')
124 enum_end_re = re.compile(r'^\s*}\s*;\.*$') 124 enum_end_re = re.compile(r'^\s*}\s*;\.*$')
125 generator_directive_re = re.compile( 125 generator_directive_re = re.compile(
126 r'^\s*//\s+GENERATED_JAVA_(\w+)\s*:\s*([\.\w]+)$') 126 r'^\s*//\s+GENERATED_JAVA_(\w+)\s*:\s*([\.\w]+)$')
127 multi_line_generator_directive_start_re = re.compile(
128 r'^\s*//\s+GENERATED_JAVA_(\w+)\s*:\s*([\.\w]*)\\$')
129 multi_line_directive_continuation_re = re.compile(
130 r'^\s*//\s+([\.\w]+)\\$')
131 multi_line_directive_end_re = re.compile(
132 r'^\s*//\s+([\.\w]*)$')
127 133
128 optional_class_or_struct_re = r'(class|struct)?' 134 optional_class_or_struct_re = r'(class|struct)?'
129 enum_name_re = r'(\w+)' 135 enum_name_re = r'(\w+)'
130 optional_fixed_type_re = r'(\:\s*(\w+\s*\w+?))?' 136 optional_fixed_type_re = r'(\:\s*(\w+\s*\w+?))?'
131 enum_start_re = re.compile(r'^\s*enum\s+' + optional_class_or_struct_re + 137 enum_start_re = re.compile(r'^\s*enum\s+' + optional_class_or_struct_re +
132 '\s*' + enum_name_re + '\s*' + optional_fixed_type_re + '\s*{\s*$') 138 '\s*' + enum_name_re + '\s*' + optional_fixed_type_re + '\s*{\s*$')
133 139
134 def __init__(self, lines): 140 def __init__(self, lines, path=None):
135 self._lines = lines 141 self._lines = lines
142 self._path = path
136 self._enum_definitions = [] 143 self._enum_definitions = []
137 self._in_enum = False 144 self._in_enum = False
138 self._current_definition = None 145 self._current_definition = None
139 self._generator_directives = DirectiveSet() 146 self._generator_directives = DirectiveSet()
147 self._multi_line_generator_directive = None
140 148
141 def ParseDefinitions(self): 149 def ParseDefinitions(self):
142 for line in self._lines: 150 for line in self._lines:
143 self._ParseLine(line) 151 self._ParseLine(line)
144 return self._enum_definitions 152 return self._enum_definitions
145 153
146 def _ParseLine(self, line): 154 def _ParseLine(self, line):
147 if not self._in_enum: 155 if not self._in_enum:
148 self._ParseRegularLine(line) 156 self._ParseRegularLine(line)
149 else: 157 else:
150 self._ParseEnumLine(line) 158 self._ParseEnumLine(line)
151 159
152 def _ParseEnumLine(self, line): 160 def _ParseEnumLine(self, line):
153 if HeaderParser.single_line_comment_re.match(line): 161 if HeaderParser.single_line_comment_re.match(line):
154 return 162 return
155 if HeaderParser.multi_line_comment_start_re.match(line): 163 if HeaderParser.multi_line_comment_start_re.match(line):
156 raise Exception('Multi-line comments in enums are not supported.') 164 raise Exception('Multi-line comments in enums are not supported in ' +
165 self._path)
157 enum_end = HeaderParser.enum_end_re.match(line) 166 enum_end = HeaderParser.enum_end_re.match(line)
158 enum_entry = HeaderParser.enum_line_re.match(line) 167 enum_entry = HeaderParser.enum_line_re.match(line)
159 if enum_end: 168 if enum_end:
160 self._ApplyGeneratorDirectives() 169 self._ApplyGeneratorDirectives()
161 self._current_definition.Finalize() 170 self._current_definition.Finalize()
162 self._enum_definitions.append(self._current_definition) 171 self._enum_definitions.append(self._current_definition)
163 self._in_enum = False 172 self._in_enum = False
164 elif enum_entry: 173 elif enum_entry:
165 enum_key = enum_entry.groups()[0] 174 enum_key = enum_entry.groups()[0]
166 enum_value = enum_entry.groups()[2] 175 enum_value = enum_entry.groups()[2]
167 self._current_definition.AppendEntry(enum_key, enum_value) 176 self._current_definition.AppendEntry(enum_key, enum_value)
168 177
169 def _ApplyGeneratorDirectives(self): 178 def _ApplyGeneratorDirectives(self):
170 self._generator_directives.UpdateDefinition(self._current_definition) 179 self._generator_directives.UpdateDefinition(self._current_definition)
171 self._generator_directives = DirectiveSet() 180 self._generator_directives = DirectiveSet()
172 181
173 def _ParseRegularLine(self, line): 182 def _ParseRegularLine(self, line):
174 enum_start = HeaderParser.enum_start_re.match(line) 183 enum_start = HeaderParser.enum_start_re.match(line)
jbudorick 2015/01/09 16:39:17 nit: you don't need to run these three regexes if
mkosiba (inactive) 2015/01/09 17:09:57 Done.
175 generator_directive = HeaderParser.generator_directive_re.match(line) 184 generator_directive = HeaderParser.generator_directive_re.match(line)
176 if enum_start: 185 multi_line_generator_directive_start = (
186 HeaderParser.multi_line_generator_directive_start_re.match(line))
187
188 if self._multi_line_generator_directive:
189 multi_line_directive_continuation = (
190 HeaderParser.multi_line_directive_continuation_re.match(line))
191 multi_line_directive_end = (
192 HeaderParser.multi_line_directive_end_re.match(line))
193
194 if multi_line_directive_continuation:
195 value_cont = multi_line_directive_continuation.groups()[0]
196 self._multi_line_generator_directive[1].append(value_cont)
197 elif multi_line_directive_end:
198 directive_name = self._multi_line_generator_directive[0]
199 directive_value = "".join(self._multi_line_generator_directive[1])
200 directive_value += multi_line_directive_end.groups()[0]
201 self._multi_line_generator_directive = None
202 self._generator_directives.Update(directive_name, directive_value)
203 else:
204 raise Exception('Malformed multi-line directive declaration in ' +
205 self._path)
206 elif generator_directive:
207 directive_name = generator_directive.groups()[0]
208 directive_value = generator_directive.groups()[1]
209 self._generator_directives.Update(directive_name, directive_value)
210 elif multi_line_generator_directive_start:
211 directive_name = multi_line_generator_directive_start.groups()[0]
212 directive_value = multi_line_generator_directive_start.groups()[1]
213 self._multi_line_generator_directive = (directive_name, [directive_value])
214 elif enum_start:
177 if self._generator_directives.empty: 215 if self._generator_directives.empty:
178 return 216 return
179 self._current_definition = EnumDefinition( 217 self._current_definition = EnumDefinition(
180 original_enum_name=enum_start.groups()[1], 218 original_enum_name=enum_start.groups()[1],
181 fixed_type=enum_start.groups()[3]) 219 fixed_type=enum_start.groups()[3])
182 self._in_enum = True 220 self._in_enum = True
183 elif generator_directive:
184 directive_name = generator_directive.groups()[0]
185 directive_value = generator_directive.groups()[1]
186 self._generator_directives.Update(directive_name, directive_value)
187
188 221
189 def GetScriptName(): 222 def GetScriptName():
190 script_components = os.path.abspath(sys.argv[0]).split(os.path.sep) 223 script_components = os.path.abspath(sys.argv[0]).split(os.path.sep)
191 build_index = script_components.index('build') 224 build_index = script_components.index('build')
192 return os.sep.join(script_components[build_index:]) 225 return os.sep.join(script_components[build_index:])
193 226
194 227
195 def DoGenerate(options, source_paths): 228 def DoGenerate(options, source_paths):
196 output_paths = [] 229 output_paths = []
197 for source_path in source_paths: 230 for source_path in source_paths:
198 enum_definitions = DoParseHeaderFile(source_path) 231 enum_definitions = DoParseHeaderFile(source_path)
199 for enum_definition in enum_definitions: 232 for enum_definition in enum_definitions:
200 package_path = enum_definition.enum_package.replace('.', os.path.sep) 233 package_path = enum_definition.enum_package.replace('.', os.path.sep)
201 file_name = enum_definition.class_name + '.java' 234 file_name = enum_definition.class_name + '.java'
202 output_path = os.path.join(options.output_dir, package_path, file_name) 235 output_path = os.path.join(options.output_dir, package_path, file_name)
203 output_paths.append(output_path) 236 output_paths.append(output_path)
204 if not options.print_output_only: 237 if not options.print_output_only:
205 build_utils.MakeDirectory(os.path.dirname(output_path)) 238 build_utils.MakeDirectory(os.path.dirname(output_path))
206 DoWriteOutput(source_path, output_path, enum_definition) 239 DoWriteOutput(source_path, output_path, enum_definition)
207 return output_paths 240 return output_paths
208 241
209 242
210 def DoParseHeaderFile(path): 243 def DoParseHeaderFile(path):
211 with open(path) as f: 244 with open(path) as f:
212 return HeaderParser(f.readlines()).ParseDefinitions() 245 return HeaderParser(f.readlines(), path).ParseDefinitions()
213 246
214 247
215 def GenerateOutput(source_path, enum_definition): 248 def GenerateOutput(source_path, enum_definition):
216 template = Template(""" 249 template = Template("""
217 // Copyright 2014 The Chromium Authors. All rights reserved. 250 // Copyright 2014 The Chromium Authors. All rights reserved.
218 // Use of this source code is governed by a BSD-style license that can be 251 // Use of this source code is governed by a BSD-style license that can be
219 // found in the LICENSE file. 252 // found in the LICENSE file.
220 253
221 // This file is autogenerated by 254 // This file is autogenerated by
222 // ${SCRIPT_NAME} 255 // ${SCRIPT_NAME}
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
278 311
279 output_paths = DoGenerate(options, args) 312 output_paths = DoGenerate(options, args)
280 313
281 if options.assert_files_list: 314 if options.assert_files_list:
282 AssertFilesList(output_paths, options.assert_files_list) 315 AssertFilesList(output_paths, options.assert_files_list)
283 316
284 return " ".join(output_paths) 317 return " ".join(output_paths)
285 318
286 if __name__ == '__main__': 319 if __name__ == '__main__':
287 DoMain(sys.argv[1:]) 320 DoMain(sys.argv[1:])
OLDNEW
« no previous file with comments | « no previous file | build/android/gyp/java_cpp_enum_tests.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698