#!/usr/bin/env python # Copyright (C) 2010 Google Inc. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in the # documentation and/or other materials provided with the distribution. # # THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY # EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR # PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR # CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, # EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, # PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR # PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY # OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. from __future__ import with_statement import glob import logging import optparse import os import re import sys from webkitpy.common.checkout import scm _log = logging.getLogger("webkitpy.layout_tests." "update-webgl-conformance-tests") def remove_first_line_comment(text): return re.compile(r'^\s*', re.DOTALL).sub('', text) def translate_includes(text): # Mapping of single filename to relative path under WebKit root. # Assumption: these filenames are globally unique. include_mapping = { "js-test-style.css": "../../js/resources", "js-test-pre.js": "../../js/resources", "js-test-post.js": "../../js/resources", "desktop-gl-constants.js": "resources", } for filename, path in include_mapping.items(): search = r'(?:[^"\'= ]*/)?' + re.escape(filename) # We use '/' instead of os.path.join in order to produce consistent # output cross-platform. replace = path + '/' + filename text = re.sub(search, replace, text) return text def translate_khronos_test(text): """ This method translates the contents of a Khronos test to a WebKit test. """ translateFuncs = [ remove_first_line_comment, translate_includes, ] for f in translateFuncs: text = f(text) return text def update_file(in_filename, out_dir): # check in_filename exists # check out_dir exists out_filename = os.path.join(out_dir, os.path.basename(in_filename)) _log.debug("Processing " + in_filename) with open(in_filename, 'r') as in_file: with open(out_filename, 'w') as out_file: out_file.write(translate_khronos_test(in_file.read())) def update_directory(in_dir, out_dir): for filename in glob.glob(os.path.join(in_dir, '*.html')): update_file(os.path.join(in_dir, filename), out_dir) def default_out_dir(): current_scm = scm.detect_scm_system(os.path.dirname(sys.argv[0])) if not current_scm: return os.getcwd() root_dir = current_scm.checkout_root if not root_dir: return os.getcwd() out_dir = os.path.join(root_dir, "LayoutTests/fast/canvas/webgl") if os.path.isdir(out_dir): return out_dir return os.getcwd() def configure_logging(options): """Configures the logging system.""" log_fmt = '%(levelname)s: %(message)s' log_datefmt = '%y%m%d %H:%M:%S' log_level = logging.INFO if options.verbose: log_fmt = ('%(asctime)s %(filename)s:%(lineno)-4d %(levelname)s ' '%(message)s') log_level = logging.DEBUG logging.basicConfig(level=log_level, format=log_fmt, datefmt=log_datefmt) def option_parser(): usage = "usage: %prog [options] (input file or directory)" parser = optparse.OptionParser(usage=usage) parser.add_option('-v', '--verbose', action='store_true', default=False, help='include debug-level logging') parser.add_option('-o', '--output', action='store', type='string', default=default_out_dir(), metavar='DIR', help='specify an output directory to place files ' 'in [default: %default]') return parser def main(): parser = option_parser() (options, args) = parser.parse_args() configure_logging(options) if len(args) == 0: _log.error("Must specify an input directory or filename.") parser.print_help() return 1 in_name = args[0] if os.path.isfile(in_name): update_file(in_name, options.output) elif os.path.isdir(in_name): update_directory(in_name, options.output) else: _log.error("'%s' is not a directory or a file.", in_name) return 2 return 0 if __name__ == "__main__": sys.exit(main())