1#!/usr/bin/env python 2# Copyright 2014 The Chromium 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"""Takes the JSON files in components/domain_reliability/baked_in_configs and 8encodes their contents as an array of C strings that gets compiled in to Chrome 9and loaded at runtime.""" 10 11 12import json 13import os 14import sys 15 16 17# A whitelist of domains that the script will accept when baking configs in to 18# Chrome, to ensure incorrect ones are not added accidentally. Subdomains of 19# whitelist entries are also allowed (e.g. maps.google.com, ssl.gstatic.com). 20DOMAIN_WHITELIST = ('2mdn.net', 'admob.com', 'doubleclick.net', 'ggpht.com', 21 'google.cn', 'google.co.uk', 'google.com', 'google.com.au', 22 'google.de', 'google.fr', 'google.it', 'google.jp', 23 'google.org', 'google.ru', 'googleadservices.com', 24 'googleapis.com', 'googlesyndication.com', 25 'googleusercontent.com', 'googlevideo.com', 'gstatic.com', 26 'gvt1.com', 'youtube.com', 'ytimg.com') 27 28 29CC_HEADER = """// Copyright (C) 2014 The Chromium Authors. All rights reserved. 30// Use of this source code is governed by a BSD-style license that can be 31// found in the LICENSE file. 32 33// AUTOGENERATED FILE. DO NOT EDIT. 34// 35// (Update configs in components/domain_reliability/baked_in_configs and list 36// configs in components/domain_reliability.gypi instead.) 37 38#include "components/domain_reliability/baked_in_configs.h" 39 40#include <stdlib.h> 41 42namespace domain_reliability { 43 44const char* const kBakedInJsonConfigs[] = { 45""" 46 47 48CC_FOOTER = """ NULL 49}; 50 51} // namespace domain_reliability 52""" 53 54 55def domain_is_whitelisted(domain): 56 return any(domain == e or domain.endswith('.' + e) for e in DOMAIN_WHITELIST) 57 58 59def quote_and_wrap_text(text, width=79, prefix=' "', suffix='"'): 60 max_length = width - len(prefix) - len(suffix) 61 output = prefix 62 line_length = 0 63 for c in text: 64 if c == "\"": 65 c = "\\\"" 66 elif c == "\n": 67 c = "\\n" 68 elif c == "\\": 69 c = "\\\\" 70 if line_length + len(c) > max_length: 71 output += suffix + "\n" + prefix 72 line_length = 0 73 output += c 74 line_length += len(c) 75 output += suffix 76 return output 77 78 79def main(): 80 if len(sys.argv) < 3: 81 print >> sys.stderr, ('Usage: %s <JSON files...> <output C++ file>' % 82 sys.argv[0]) 83 print >> sys.stderr, sys.modules[__name__].__doc__ 84 return 1 85 86 cpp_code = CC_HEADER 87 found_invalid_config = False 88 for json_file in sys.argv[1:-1]: 89 with open(json_file, 'r') as f: 90 json_text = f.read() 91 config = json.loads(json_text) 92 if 'monitored_domain' not in config: 93 print >> sys.stderr, ('%s: no monitored_domain found' % json_file) 94 found_invalid_config = True 95 continue 96 domain = config['monitored_domain'] 97 if not domain_is_whitelisted(domain): 98 print >> sys.stderr, ('%s: monitored_domain "%s" not in whitelist' % 99 (json_file, domain)) 100 found_invalid_config = True 101 continue 102 cpp_code += " // " + json_file + ":\n" 103 cpp_code += quote_and_wrap_text(json_text) + ",\n" 104 cpp_code += "\n" 105 cpp_code += CC_FOOTER 106 107 if found_invalid_config: 108 return 1 109 110 with open(sys.argv[-1], 'wb') as f: 111 f.write(cpp_code) 112 113 return 0 114 115 116if __name__ == '__main__': 117 sys.exit(main()) 118