11cb0ef41Sopenharmony_ci# Copyright 2018 The Chromium Authors. All rights reserved. 21cb0ef41Sopenharmony_ci# Use of this source code is governed by a BSD-style license that can be 31cb0ef41Sopenharmony_ci# found in the LICENSE file. 41cb0ef41Sopenharmony_ci 51cb0ef41Sopenharmony_cifrom __future__ import print_function 61cb0ef41Sopenharmony_ciimport collections 71cb0ef41Sopenharmony_ciimport json 81cb0ef41Sopenharmony_ciimport os.path 91cb0ef41Sopenharmony_ciimport re 101cb0ef41Sopenharmony_ciimport sys 111cb0ef41Sopenharmony_ci 121cb0ef41Sopenharmony_cidescription = '' 131cb0ef41Sopenharmony_ci 141cb0ef41Sopenharmony_ci 151cb0ef41Sopenharmony_ciprimitiveTypes = ['integer', 'number', 'boolean', 'string', 'object', 'any', 'array', 'binary'] 161cb0ef41Sopenharmony_ci 171cb0ef41Sopenharmony_ci 181cb0ef41Sopenharmony_cidef assignType(item, type, is_array=False, map_binary_to_string=False): 191cb0ef41Sopenharmony_ci if is_array: 201cb0ef41Sopenharmony_ci item['type'] = 'array' 211cb0ef41Sopenharmony_ci item['items'] = collections.OrderedDict() 221cb0ef41Sopenharmony_ci assignType(item['items'], type, False, map_binary_to_string) 231cb0ef41Sopenharmony_ci return 241cb0ef41Sopenharmony_ci 251cb0ef41Sopenharmony_ci if type == 'enum': 261cb0ef41Sopenharmony_ci type = 'string' 271cb0ef41Sopenharmony_ci if map_binary_to_string and type == 'binary': 281cb0ef41Sopenharmony_ci type = 'string' 291cb0ef41Sopenharmony_ci if type in primitiveTypes: 301cb0ef41Sopenharmony_ci item['type'] = type 311cb0ef41Sopenharmony_ci else: 321cb0ef41Sopenharmony_ci item['$ref'] = type 331cb0ef41Sopenharmony_ci 341cb0ef41Sopenharmony_ci 351cb0ef41Sopenharmony_cidef createItem(d, experimental, deprecated, name=None): 361cb0ef41Sopenharmony_ci result = collections.OrderedDict(d) 371cb0ef41Sopenharmony_ci if name: 381cb0ef41Sopenharmony_ci result['name'] = name 391cb0ef41Sopenharmony_ci global description 401cb0ef41Sopenharmony_ci if description: 411cb0ef41Sopenharmony_ci result['description'] = description.strip() 421cb0ef41Sopenharmony_ci if experimental: 431cb0ef41Sopenharmony_ci result['experimental'] = True 441cb0ef41Sopenharmony_ci if deprecated: 451cb0ef41Sopenharmony_ci result['deprecated'] = True 461cb0ef41Sopenharmony_ci return result 471cb0ef41Sopenharmony_ci 481cb0ef41Sopenharmony_ci 491cb0ef41Sopenharmony_cidef parse(data, file_name, map_binary_to_string=False): 501cb0ef41Sopenharmony_ci protocol = collections.OrderedDict() 511cb0ef41Sopenharmony_ci protocol['version'] = collections.OrderedDict() 521cb0ef41Sopenharmony_ci protocol['domains'] = [] 531cb0ef41Sopenharmony_ci domain = None 541cb0ef41Sopenharmony_ci item = None 551cb0ef41Sopenharmony_ci subitems = None 561cb0ef41Sopenharmony_ci nukeDescription = False 571cb0ef41Sopenharmony_ci global description 581cb0ef41Sopenharmony_ci lines = data.split('\n') 591cb0ef41Sopenharmony_ci for i in range(0, len(lines)): 601cb0ef41Sopenharmony_ci if nukeDescription: 611cb0ef41Sopenharmony_ci description = '' 621cb0ef41Sopenharmony_ci nukeDescription = False 631cb0ef41Sopenharmony_ci line = lines[i] 641cb0ef41Sopenharmony_ci trimLine = line.strip() 651cb0ef41Sopenharmony_ci 661cb0ef41Sopenharmony_ci if trimLine.startswith('#'): 671cb0ef41Sopenharmony_ci if len(description): 681cb0ef41Sopenharmony_ci description += '\n' 691cb0ef41Sopenharmony_ci description += trimLine[2:] 701cb0ef41Sopenharmony_ci continue 711cb0ef41Sopenharmony_ci else: 721cb0ef41Sopenharmony_ci nukeDescription = True 731cb0ef41Sopenharmony_ci 741cb0ef41Sopenharmony_ci if len(trimLine) == 0: 751cb0ef41Sopenharmony_ci continue 761cb0ef41Sopenharmony_ci 771cb0ef41Sopenharmony_ci match = re.compile(r'^(experimental )?(deprecated )?domain (.*)').match(line) 781cb0ef41Sopenharmony_ci if match: 791cb0ef41Sopenharmony_ci domain = createItem({'domain' : match.group(3)}, match.group(1), match.group(2)) 801cb0ef41Sopenharmony_ci protocol['domains'].append(domain) 811cb0ef41Sopenharmony_ci continue 821cb0ef41Sopenharmony_ci 831cb0ef41Sopenharmony_ci match = re.compile(r'^ depends on ([^\s]+)').match(line) 841cb0ef41Sopenharmony_ci if match: 851cb0ef41Sopenharmony_ci if 'dependencies' not in domain: 861cb0ef41Sopenharmony_ci domain['dependencies'] = [] 871cb0ef41Sopenharmony_ci domain['dependencies'].append(match.group(1)) 881cb0ef41Sopenharmony_ci continue 891cb0ef41Sopenharmony_ci 901cb0ef41Sopenharmony_ci match = re.compile(r'^ (experimental )?(deprecated )?type (.*) extends (array of )?([^\s]+)').match(line) 911cb0ef41Sopenharmony_ci if match: 921cb0ef41Sopenharmony_ci if 'types' not in domain: 931cb0ef41Sopenharmony_ci domain['types'] = [] 941cb0ef41Sopenharmony_ci item = createItem({'id': match.group(3)}, match.group(1), match.group(2)) 951cb0ef41Sopenharmony_ci assignType(item, match.group(5), match.group(4), map_binary_to_string) 961cb0ef41Sopenharmony_ci domain['types'].append(item) 971cb0ef41Sopenharmony_ci continue 981cb0ef41Sopenharmony_ci 991cb0ef41Sopenharmony_ci match = re.compile(r'^ (experimental )?(deprecated )?(command|event) (.*)').match(line) 1001cb0ef41Sopenharmony_ci if match: 1011cb0ef41Sopenharmony_ci list = [] 1021cb0ef41Sopenharmony_ci if match.group(3) == 'command': 1031cb0ef41Sopenharmony_ci if 'commands' in domain: 1041cb0ef41Sopenharmony_ci list = domain['commands'] 1051cb0ef41Sopenharmony_ci else: 1061cb0ef41Sopenharmony_ci list = domain['commands'] = [] 1071cb0ef41Sopenharmony_ci else: 1081cb0ef41Sopenharmony_ci if 'events' in domain: 1091cb0ef41Sopenharmony_ci list = domain['events'] 1101cb0ef41Sopenharmony_ci else: 1111cb0ef41Sopenharmony_ci list = domain['events'] = [] 1121cb0ef41Sopenharmony_ci 1131cb0ef41Sopenharmony_ci item = createItem({}, match.group(1), match.group(2), match.group(4)) 1141cb0ef41Sopenharmony_ci list.append(item) 1151cb0ef41Sopenharmony_ci continue 1161cb0ef41Sopenharmony_ci 1171cb0ef41Sopenharmony_ci match = re.compile(r'^ (experimental )?(deprecated )?(optional )?(array of )?([^\s]+) ([^\s]+)').match(line) 1181cb0ef41Sopenharmony_ci if match: 1191cb0ef41Sopenharmony_ci param = createItem({}, match.group(1), match.group(2), match.group(6)) 1201cb0ef41Sopenharmony_ci if match.group(3): 1211cb0ef41Sopenharmony_ci param['optional'] = True 1221cb0ef41Sopenharmony_ci assignType(param, match.group(5), match.group(4), map_binary_to_string) 1231cb0ef41Sopenharmony_ci if match.group(5) == 'enum': 1241cb0ef41Sopenharmony_ci enumliterals = param['enum'] = [] 1251cb0ef41Sopenharmony_ci subitems.append(param) 1261cb0ef41Sopenharmony_ci continue 1271cb0ef41Sopenharmony_ci 1281cb0ef41Sopenharmony_ci match = re.compile(r'^ (parameters|returns|properties)').match(line) 1291cb0ef41Sopenharmony_ci if match: 1301cb0ef41Sopenharmony_ci subitems = item[match.group(1)] = [] 1311cb0ef41Sopenharmony_ci continue 1321cb0ef41Sopenharmony_ci 1331cb0ef41Sopenharmony_ci match = re.compile(r'^ enum').match(line) 1341cb0ef41Sopenharmony_ci if match: 1351cb0ef41Sopenharmony_ci enumliterals = item['enum'] = [] 1361cb0ef41Sopenharmony_ci continue 1371cb0ef41Sopenharmony_ci 1381cb0ef41Sopenharmony_ci match = re.compile(r'^version').match(line) 1391cb0ef41Sopenharmony_ci if match: 1401cb0ef41Sopenharmony_ci continue 1411cb0ef41Sopenharmony_ci 1421cb0ef41Sopenharmony_ci match = re.compile(r'^ major (\d+)').match(line) 1431cb0ef41Sopenharmony_ci if match: 1441cb0ef41Sopenharmony_ci protocol['version']['major'] = match.group(1) 1451cb0ef41Sopenharmony_ci continue 1461cb0ef41Sopenharmony_ci 1471cb0ef41Sopenharmony_ci match = re.compile(r'^ minor (\d+)').match(line) 1481cb0ef41Sopenharmony_ci if match: 1491cb0ef41Sopenharmony_ci protocol['version']['minor'] = match.group(1) 1501cb0ef41Sopenharmony_ci continue 1511cb0ef41Sopenharmony_ci 1521cb0ef41Sopenharmony_ci match = re.compile(r'^ redirect ([^\s]+)').match(line) 1531cb0ef41Sopenharmony_ci if match: 1541cb0ef41Sopenharmony_ci item['redirect'] = match.group(1) 1551cb0ef41Sopenharmony_ci continue 1561cb0ef41Sopenharmony_ci 1571cb0ef41Sopenharmony_ci match = re.compile(r'^ ( )?[^\s]+$').match(line) 1581cb0ef41Sopenharmony_ci if match: 1591cb0ef41Sopenharmony_ci # enum literal 1601cb0ef41Sopenharmony_ci enumliterals.append(trimLine) 1611cb0ef41Sopenharmony_ci continue 1621cb0ef41Sopenharmony_ci 1631cb0ef41Sopenharmony_ci print('Error in %s:%s, illegal token: \t%s' % (file_name, i, line)) 1641cb0ef41Sopenharmony_ci sys.exit(1) 1651cb0ef41Sopenharmony_ci return protocol 1661cb0ef41Sopenharmony_ci 1671cb0ef41Sopenharmony_ci 1681cb0ef41Sopenharmony_cidef loads(data, file_name, map_binary_to_string=False): 1691cb0ef41Sopenharmony_ci if file_name.endswith(".pdl"): 1701cb0ef41Sopenharmony_ci return parse(data, file_name, map_binary_to_string) 1711cb0ef41Sopenharmony_ci return json.loads(data) 172