Commit 21707ea8 authored by Yipeng Wang's avatar Yipeng Wang Committed by Commit Bot

[about:credits] Make webview use chrome license file

This CL also deletes webview_licenses.py and related files.

Bug: 734846
Change-Id: Ib1dcdbd10c8c97993811e0c977bfaa68d0562315
Reviewed-on: https://chromium-review.googlesource.com/569075Reviewed-by: default avatarRichard Coles <torne@chromium.org>
Reviewed-by: default avatarPaweł Hajdan Jr. <phajdan.jr@chromium.org>
Reviewed-by: default avatarMisha Efimov <mef@chromium.org>
Reviewed-by: default avatarDirk Pranke <dpranke@chromium.org>
Commit-Queue: Yipeng Wang <yipengw@chromium.org>
Cr-Commit-Position: refs/heads/master@{#486783}
parent 82b35f8e
...@@ -180,8 +180,6 @@ repack("repack_100_percent") { ...@@ -180,8 +180,6 @@ repack("repack_100_percent") {
} }
} }
webview_license_path = "$target_gen_dir/webview_licenses.notice"
android_assets("pak_file_assets") { android_assets("pak_file_assets") {
sources = [ sources = [
"$target_gen_dir/chrome_100_percent.pak", "$target_gen_dir/chrome_100_percent.pak",
...@@ -222,28 +220,10 @@ java_group("stub_assets") { ...@@ -222,28 +220,10 @@ java_group("stub_assets") {
} }
android_assets("license_assets") { android_assets("license_assets") {
sources = [ renaming_sources = [ "$root_gen_dir/components/resources/about_credits.html" ]
webview_license_path, renaming_destinations = [ "webview_licenses.notice" ]
]
deps = [ deps = [
":generate_webview_license_notice", "//components/resources:about_credits",
]
}
action("generate_webview_license_notice") {
script = "tools/webview_licenses.py"
depfile = "$target_gen_dir/$target_name.d"
inputs = [
"tools/licenses_notice.tmpl",
]
outputs = [
webview_license_path,
]
args = [
"notice",
rebase_path(webview_license_path, root_build_dir),
"--depfile",
rebase_path(depfile, root_build_dir),
] ]
} }
......
...@@ -15,7 +15,6 @@ def CommonChecks(input_api, output_api): ...@@ -15,7 +15,6 @@ def CommonChecks(input_api, output_api):
input_api, output_api, pylintrc='pylintrc', input_api, output_api, pylintrc='pylintrc',
# TODO: lint these and eliminate the blacklist. # TODO: lint these and eliminate the blacklist.
black_list=[ black_list=[
r'webview_licenses.py',
r'webview_repack_locales.py', r'webview_repack_locales.py',
])) ]))
return input_api.RunTests(checks, False) return input_api.RunTests(checks, False)
......
#!/usr/bin/python
# Copyright 2014 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
"""Checks third-party licenses for the purposes of the Android WebView build.
The Android tree includes a snapshot of Chromium in order to power the system
WebView. This tool checks that all code uses open-source licenses compatible
with Android, and that we meet the requirements of those licenses. It can also
be used to generate an Android NOTICE file for the third-party code.
It makes use of src/tools/licenses.py and the README.chromium files on which
it depends. It also makes use of a data file, third_party_files_whitelist.txt,
which whitelists individual files which contain third-party code but which
aren't in a third-party directory with a README.chromium file.
"""
import imp
import json
import multiprocessing
import optparse
import os
import re
import sys
import textwrap
REPOSITORY_ROOT = os.path.abspath(os.path.join(
os.path.dirname(__file__), '..', '..'))
# Import third_party/PRESUBMIT.py via imp to avoid importing a random
# PRESUBMIT.py from $PATH, also make sure we don't generate a .pyc file.
sys.dont_write_bytecode = True
third_party = \
imp.load_source('PRESUBMIT', \
os.path.join(REPOSITORY_ROOT, 'third_party', 'PRESUBMIT.py'))
sys.path.append(os.path.join(REPOSITORY_ROOT, 'build/android/gyp/util'))
import build_utils
sys.path.append(os.path.join(REPOSITORY_ROOT, 'third_party'))
import jinja2
sys.path.append(os.path.join(REPOSITORY_ROOT, 'tools'))
from copyright_scanner import copyright_scanner
import licenses
class InputApi(object):
def __init__(self):
self.os_path = os.path
self.os_walk = os.walk
self.re = re
self.ReadFile = _ReadFile
self.change = InputApiChange()
class InputApiChange(object):
def __init__(self):
self.RepositoryRoot = lambda: REPOSITORY_ROOT
class ScanResult(object):
Ok, Warnings, Errors = range(3)
# Needs to be a top-level function for multiprocessing
def _FindCopyrightViolations(files_to_scan_as_string):
return copyright_scanner.FindCopyrightViolations(
InputApi(), REPOSITORY_ROOT, files_to_scan_as_string)
def _ShardList(l, shard_len):
return [l[i:i + shard_len] for i in range(0, len(l), shard_len)]
def _CheckLicenseHeaders(excluded_dirs_list, whitelisted_files):
"""Checks that all files which are not in a listed third-party directory,
and which do not use the standard Chromium license, are whitelisted.
Args:
excluded_dirs_list: The list of directories to exclude from scanning.
whitelisted_files: The whitelist of files.
Returns:
ScanResult.Ok if all files with non-standard license headers are whitelisted
and the whitelist contains no stale entries;
ScanResult.Warnings if there are stale entries;
ScanResult.Errors if new non-whitelisted entries found.
"""
input_api = InputApi()
files_to_scan = copyright_scanner.FindFiles(
input_api, REPOSITORY_ROOT, ['.'], excluded_dirs_list)
sharded_files_to_scan = _ShardList(files_to_scan, 2000)
pool = multiprocessing.Pool()
offending_files_chunks = pool.map_async(
_FindCopyrightViolations, sharded_files_to_scan).get(999999)
pool.close()
pool.join()
# Flatten out the result
offending_files = \
[item for sublist in offending_files_chunks for item in sublist]
(unknown, missing, stale) = copyright_scanner.AnalyzeScanResults(
input_api, whitelisted_files, offending_files)
if unknown:
print 'The following files contain a third-party license but are not in ' \
'a listed third-party directory and are not whitelisted. You must ' \
'add the following files to the whitelist.\n' \
'(Note that if the code you are adding does not actually contain ' \
'any third-party code, it may contain the word "copyright", which ' \
'should be masked out, e.g. by writing it as "copy-right")\n%s' % \
'\n'.join(sorted(unknown))
if missing:
print 'The following files are whitelisted, but do not exist.\n%s' % \
'\n'.join(sorted(missing))
if stale:
print 'The following files are whitelisted unnecessarily. You must ' \
'remove the following files from the whitelist.\n%s' % \
'\n'.join(sorted(stale))
if unknown:
code = ScanResult.Errors
elif stale or missing:
code = ScanResult.Warnings
else:
code = ScanResult.Ok
problem_paths = sorted(set(unknown + missing + stale))
return (code, problem_paths)
def _ReadFile(full_path, mode='rU'):
"""Reads a file from disk. This emulates presubmit InputApi.ReadFile func.
Args:
full_path: The path of the file to read.
Returns:
The contents of the file as a string.
"""
with open(full_path, mode) as f:
return f.read()
def _Scan():
"""Checks that license meta-data is present for all third-party code and
that all non third-party code doesn't contain external copyrighted code.
Returns:
ScanResult.Ok if everything is in order;
ScanResult.Warnings if there are non-fatal problems (e.g. stale whitelist
entries)
ScanResult.Errors otherwise.
"""
third_party_dirs = licenses.FindThirdPartyDirsWithFiles(REPOSITORY_ROOT)
problem_paths = []
# First, check designated third-party directories using src/tools/licenses.py.
all_licenses_valid = True
for path in sorted(third_party_dirs):
try:
licenses.ParseDir(path, REPOSITORY_ROOT)
except licenses.LicenseError, e:
print 'Got LicenseError "%s" while scanning %s' % (e, path)
problem_paths.append(path)
all_licenses_valid = False
# Second, check for non-standard license text.
whitelisted_files = copyright_scanner.LoadWhitelistedFilesList(InputApi())
licenses_check, more_problem_paths = _CheckLicenseHeaders(
third_party_dirs, whitelisted_files)
problem_paths.extend(more_problem_paths)
return (licenses_check if all_licenses_valid else ScanResult.Errors,
problem_paths)
class TemplateEntryGenerator(object):
def __init__(self):
self._toc_index = 0
def _ReadFileGuessEncoding(self, name):
contents = ''
with open(name, 'rb') as input_file:
contents = input_file.read()
try:
return contents.decode('utf8')
except UnicodeDecodeError:
pass
# If it's not UTF-8, it must be CP-1252. Fail otherwise.
return contents.decode('cp1252')
def MetadataToTemplateEntry(self, metadata):
self._toc_index += 1
return {
'name': metadata['Name'],
'url': metadata['URL'],
'license_file': metadata['License File'],
'license': self._ReadFileGuessEncoding(metadata['License File']),
'toc_href': 'entry' + str(self._toc_index),
}
def GenerateNoticeFile():
"""Generates the contents of an Android NOTICE file for the third-party code.
This is used by the snapshot tool.
Returns:
A tuple of (input paths, contents of the NOTICE file).
"""
generator = TemplateEntryGenerator()
# Start from Chromium's LICENSE file
entries = [generator.MetadataToTemplateEntry({
'Name': 'The Chromium Project',
'URL': 'http://www.chromium.org',
'License File': os.path.join(REPOSITORY_ROOT, 'LICENSE') })
]
third_party_dirs = licenses.FindThirdPartyDirsWithFiles(REPOSITORY_ROOT)
# We provide attribution for all third-party directories.
# TODO(mnaganov): Limit this to only code used by the WebView binary.
for directory in sorted(third_party_dirs):
try:
metadata = licenses.ParseDir(directory, REPOSITORY_ROOT,
require_license_file=False)
except licenses.LicenseError:
# Since this code is called during project files generation,
# we don't want to break the it. But we assume that release
# WebView apks are built using checkouts that pass
# 'webview_licenses.py scan' check, thus they don't contain
# projects with non-compatible licenses.
continue
license_file = metadata['License File']
if license_file and license_file != licenses.NOT_SHIPPED:
entries.append(generator.MetadataToTemplateEntry(metadata))
entries.sort(key=lambda entry: entry['name'])
license_file_list = sorted(set([entry['license_file'] for entry in entries]))
license_file_list = [os.path.relpath(p) for p in license_file_list]
env = jinja2.Environment(
loader=jinja2.FileSystemLoader(os.path.dirname(__file__)),
extensions=['jinja2.ext.autoescape'])
template = env.get_template('licenses_notice.tmpl')
notice_file_contents = template.render({'entries': entries}).encode('utf8')
return (license_file_list, notice_file_contents)
def main():
class FormatterWithNewLines(optparse.IndentedHelpFormatter):
def format_description(self, description):
paras = description.split('\n')
formatted_paras = [textwrap.fill(para, self.width) for para in paras]
return '\n'.join(formatted_paras) + '\n'
parser = optparse.OptionParser(formatter=FormatterWithNewLines(),
usage='%prog [options]')
parser.add_option('--json', help='Path to JSON output file')
build_utils.AddDepfileOption(parser)
parser.description = (__doc__ +
'\nCommands:\n'
' scan Check licenses.\n'
'Android NOTICE file.\n'
' notice [file] Generate Android NOTICE file on '
'stdout or into |file|.\n'
' display_copyrights Display autorship on the files'
' using names provided via stdin.\n')
options, args = parser.parse_args()
if len(args) < 1:
parser.print_help()
return ScanResult.Errors
if args[0] == 'scan':
scan_result, problem_paths = _Scan()
if scan_result == ScanResult.Ok:
print 'OK!'
if options.json:
with open(options.json, 'w') as f:
json.dump(problem_paths, f)
return scan_result
elif args[0] == 'notice':
license_file_list, notice_file_contents = GenerateNoticeFile()
if len(args) == 1:
print notice_file_contents
else:
with open(args[1], 'w') as output_file:
output_file.write(notice_file_contents)
if options.depfile:
assert args[1]
# Add in build.ninja so that the target will be considered dirty whenever
# gn gen is run. Otherwise, it will fail to notice new files being added.
# This is still no perfect, as it will fail if no build files are changed,
# but a new README.chromium / LICENSE is added. This shouldn't happen in
# practice however.
build_utils.WriteDepfile(options.depfile, args[1],
license_file_list + ['build.ninja'])
return ScanResult.Ok
elif args[0] == 'display_copyrights':
files = sys.stdin.read().splitlines()
for f, c in \
zip(files, copyright_scanner.FindCopyrights(InputApi(), '.', files)):
print f, '\t', ' / '.join(sorted(c))
return ScanResult.Ok
parser.print_help()
return ScanResult.Errors
if __name__ == '__main__':
sys.exit(main())
...@@ -67,10 +67,6 @@ Run the following scripts: ...@@ -67,10 +67,6 @@ Run the following scripts:
about:credits page in Google Chrome builds. about:credits page in Google Chrome builds.
* `src/tools/checklicenses/checklicenses.py` - See below for info on how to * `src/tools/checklicenses/checklicenses.py` - See below for info on how to
handle possible failures. handle possible failures.
* If you are adding code that will be present in the content layer, please make
sure that the license used is compliant with Android tree requirements because
this code will also be used in Android WebView. You need to run
`src/android_webview/tools/webview_licenses.py scan`
See the ["Odds n' Ends"](adding_to_third_party.md#Odds-n_Ends) Section below if See the ["Odds n' Ends"](adding_to_third_party.md#Odds-n_Ends) Section below if
you run into any failures running these. you run into any failures running these.
...@@ -187,16 +183,3 @@ __If the failure looks like ... ... the right action is to ... __ ...@@ -187,16 +183,3 @@ __If the failure looks like ... ... the right action is to ... __
resulting binaries can't use GPL code. Ideally we just shouldn't have resulting binaries can't use GPL code. Ideally we just shouldn't have
those files at all in the tree. If in doubt, please ask mal@chromium.org those files at all in the tree. If in doubt, please ask mal@chromium.org
### Handling `webview_licenses.py` failures
__If the failure looks like ... ... the right action is to ... __
* Missing license file
* Make sure that the license file is present. It should be called 'LICENSE',
or otherwise README.chromium file must point to it explicitly.
* The following files contain a third-party license but are not in a listed
third-party directory...
* Check if it's a false positive (e.g. 'copyright' word used in a string
literal), if so, update
[src/tools/copyright_scanner/third_party_files_whitelist.txt](https://code.google.com/p/chromium/codesearch#chromium/src/tools/copyright_scanner/third_party_files_whitelist.txt)
file. Otherwise, please move the code into third_party.
#!/usr/bin/env python
# Copyright 2015 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
import json
import os
import sys
import common
def main_run(args):
with common.temporary_file() as tempfile_path:
rc = common.run_command([
os.path.join(common.SRC_DIR, 'android_webview', 'tools',
'webview_licenses.py'),
'scan',
'--json', tempfile_path
])
with open(tempfile_path) as f:
results = json.load(f)
json.dump({
'valid': True,
'failures': results,
}, args.output)
return rc
def main_compile_targets(args):
json.dump([], args.output)
if __name__ == '__main__':
funcs = {
'run': main_run,
'compile_targets': main_compile_targets,
}
sys.exit(common.run_script(sys.argv[1:], funcs))
...@@ -39,7 +39,9 @@ per-file include_tracer.py=thakis@chromium.org ...@@ -39,7 +39,9 @@ per-file include_tracer.py=thakis@chromium.org
per-file ipc_messages_log.py=yfriedman@chromium.org per-file ipc_messages_log.py=yfriedman@chromium.org
per-file licenses.py=file://tools/copyright_scanner/OWNERS per-file licenses.py=phajdan.jr@chromium.org
per-file licenses.py=sgurun@chromium.org
per-file licenses.py=torne@chromium.org
per-file remove_stale_pyc_files.py=dtu@chromium.org per-file remove_stale_pyc_files.py=dtu@chromium.org
......
# Copyright 2014 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
def CheckChangeOnUpload(input_api, output_api):
return _CommonChecks(input_api, output_api)
def CheckChangeOnCommit(input_api, output_api):
return _CommonChecks(input_api, output_api)
def _CommonChecks(input_api, output_api):
"""Checks common to both upload and commit."""
results = []
would_affect_tests = [
'PRESUBMIT.py',
'copyright_scanner.py',
'copyright_scanner_unittest.py'
]
need_to_run_unittests = False
for f in input_api.AffectedFiles():
if any(t for t in would_affect_tests if f.LocalPath().endswith(t)):
need_to_run_unittests = True
break
tests = [input_api.os_path.join(
input_api.PresubmitLocalPath(), 'copyright_scanner_unittest.py')]
results.extend(
input_api.canned_checks.RunUnitTests(input_api, output_api, tests))
return results
#!/usr/bin/env python
# Copyright 2015 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
__all__ = ['copyright_scanner']
# Copyright 2014 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
"""Utilities for scanning source files to determine code authorship.
"""
import itertools
def ForwardSlashesToOsPathSeps(input_api, path):
"""Converts forward slashes ('/') in the input path to OS-specific
path separators. Used when the paths come from outside and are using
UNIX path separators. Only works for relative paths!
Args:
input_api: InputAPI, as in presubmit scripts.
path: The path to convert.
Returns:
Converted path.
"""
return input_api.os_path.join(*path.split('/'))
def FindFiles(input_api, root_dir, start_paths_list, excluded_dirs_list):
"""Similar to UNIX utility find(1), searches for files in the directories.
Automatically leaves out only source code files and excludes third_party
directories.
Args:
input_api: InputAPI, as in presubmit scripts.
root_dir: The root directory, to which all other paths are relative.
start_paths_list: The list of paths to start search from. Each path can
be a file or a directory.
excluded_dirs_list: The list of directories to skip.
Returns:
The list of source code files found, relative to |root_dir|.
"""
excluded_dirs_list = [d for d in excluded_dirs_list if not 'third_party' in d]
# Using a common pattern for third-partyies makes the ignore regexp shorter
excluded_dirs_list.append('third_party')
path_join = input_api.os_path.join
EXTRA_EXCLUDED_DIRS = [
# VCS dirs
path_join('.git'),
path_join('.svn'),
# Build output
path_join('out', 'Debug'),
path_join('out', 'Release'),
# 'Copyright' appears in license agreements
path_join('chrome', 'app', 'resources'),
# Quickoffice js files from internal src used on buildbots.
# crbug.com/350472.
path_join('chrome', 'browser', 'resources', 'chromeos', 'quickoffice'),
# blink style copy right headers.
path_join('content', 'shell', 'renderer', 'test_runner'),
# blink style copy right headers.
path_join('content', 'shell', 'tools', 'plugin'),
# This is tests directory, doesn't exist in the snapshot
path_join('content', 'test', 'data'),
# This is a tests directory that doesn't exist in the shipped product.
path_join('gin', 'test'),
# This is a test output directory
path_join('data', 'dom_perf'),
# This is a tests directory that doesn't exist in the shipped product.
path_join('tools', 'perf', 'page_sets'),
path_join('tools', 'perf', 'page_sets', 'tough_animation_cases'),
# Histogram tools, doesn't exist in the snapshot
path_join('tools', 'histograms'),
# Swarming tools, doesn't exist in the snapshot
path_join('tools', 'swarming_client'),
# Don't check downloaded goma client binaries.
path_join('build', 'goma', 'client'),
# Ignore sysroots.
path_join('build', 'linux', 'debian_jessie_arm64-sysroot'),
path_join('build', 'linux', 'debian_jessie_arm-sysroot'),
path_join('build', 'linux', 'debian_jessie_mips-sysroot'),
path_join('build', 'linux', 'debian_jessie_i386-sysroot'),
path_join('build', 'linux', 'debian_jessie_amd64-sysroot'),
# Data is not part of open source chromium, but are included on some bots.
path_join('data'),
# This is not part of open source chromium, but are included on some bots.
path_join('skia', 'tools', 'clusterfuzz-data'),
# Not shipped, only relates to Chrome for Android, but not to WebView
path_join('clank'),
# Internal-only repository.
path_join('remoting', 'android', 'internal'),
]
excluded_dirs_list.extend(EXTRA_EXCLUDED_DIRS)
# Surround the directory names with OS path separators.
dirs_blacklist = [path_join('.', d, '')[1:] for d in excluded_dirs_list if d]
def IsBlacklistedDir(d):
for item in dirs_blacklist:
if item in d:
return True
return False
files_whitelist_re = input_api.re.compile(
r'\.(asm|c(c|pp|xx)?|h(h|pp|xx)?|p(l|m)|xs|sh|php|py(|x)'
'|rb|idl|java|el|sc(i|e)|cs|pas|inc|js|pac|html|dtd|xsl|mod|mm?'
'|tex|mli?)$')
files = []
base_path_len = len(root_dir)
for path in start_paths_list:
full_path = path_join(root_dir, path)
if input_api.os_path.isfile(full_path):
if files_whitelist_re.search(path) and \
not IsBlacklistedDir(full_path[base_path_len:]): # Keep '/' prefix.
files.append(path)
else:
for dirpath, dirnames, filenames in input_api.os_walk(full_path):
# Remove excluded subdirs for faster scanning.
for item in dirnames[:]:
if IsBlacklistedDir(
path_join(dirpath, item)[base_path_len + 1:]):
dirnames.remove(item)
for filename in filenames:
filepath = \
path_join(dirpath, filename)[base_path_len + 1:]
if files_whitelist_re.search(filepath) and \
not IsBlacklistedDir(filepath):
files.append(filepath)
return files
class _GeneratedFilesDetector(object):
GENERATED_FILE = 'GENERATED FILE'
NO_COPYRIGHT = '*No copyright*'
def __init__(self, input_api):
self.python_multiline_string_double_re = \
input_api.re.compile(r'"""[^"]*(?:"""|$)', flags=input_api.re.MULTILINE)
self.python_multiline_string_single_re = \
input_api.re.compile(r"'''[^']*(?:'''|$)", flags=input_api.re.MULTILINE)
self.automatically_generated_re = input_api.re.compile(
r'(All changes made in this file will be lost'
'|DO NOT (EDIT|delete this file)'
'|Generated (at|automatically|data)'
'|Automatically generated'
'|\Wgenerated\s+(?:\w+\s+)*file\W)', flags=input_api.re.IGNORECASE)
def IsGeneratedFile(self, header):
header = header.upper()
if '"""' in header:
header = self.python_multiline_string_double_re.sub('', header)
if "'''" in header:
header = self.python_multiline_string_single_re.sub('', header)
# First do simple strings lookup to save time.
if 'ALL CHANGES MADE IN THIS FILE WILL BE LOST' in header:
return True
if 'DO NOT EDIT' in header or 'DO NOT DELETE' in header or \
'GENERATED' in header:
return self.automatically_generated_re.search(header)
return False
class _CopyrightsScanner(object):
@staticmethod
def StaticInit(input_api):
_CopyrightsScanner._c_comment_re = \
input_api.re.compile(r'''"[^"\\]*(?:\\.[^"\\]*)*"''')
_CopyrightsScanner._copyright_indicator = \
r'(?:copyright|copr\.|\xc2\xa9|\(c\))'
_CopyrightsScanner._full_copyright_indicator_re = input_api.re.compile(
r'(?:\W|^)' + _CopyrightsScanner._copyright_indicator + \
r'(?::\s*|\s+)(\w.*)$', input_api.re.IGNORECASE)
_CopyrightsScanner._copyright_disindicator_re = input_api.re.compile(
r'\s*\b(?:info(?:rmation)?|notice|and|or)\b', input_api.re.IGNORECASE)
def __init__(self, input_api):
self.max_line_numbers_proximity = 3
self.last_a_item_line_number = -200
self.last_b_item_line_number = -100
self.re = input_api.re
def _CloseLineNumbers(self, a, b):
return 0 <= a - b <= self.max_line_numbers_proximity
def MatchLine(self, line_number, line):
if '"' in line:
line = _CopyrightsScanner._c_comment_re.sub('', line)
upcase_line = line.upper()
# Record '(a)' and '(b)' last occurences in C++ comments.
# This is to filter out '(c)' used as a list item inside C++ comments.
# E.g. "// blah-blah (a) blah\n// blah-blah (b) and (c) blah"
cpp_comment_idx = upcase_line.find('//')
if cpp_comment_idx != -1:
if upcase_line.find('(A)') > cpp_comment_idx:
self.last_a_item_line_number = line_number
if upcase_line.find('(B)') > cpp_comment_idx:
self.last_b_item_line_number = line_number
# Fast bailout, uses the same patterns as _copyright_indicator regexp.
if not 'COPYRIGHT' in upcase_line and not 'COPR.' in upcase_line \
and not '\xc2\xa9' in upcase_line:
c_item_index = upcase_line.find('(C)')
if c_item_index == -1:
return None
if c_item_index > cpp_comment_idx and \
self._CloseLineNumbers(line_number,
self.last_b_item_line_number) and \
self._CloseLineNumbers(self.last_b_item_line_number,
self.last_a_item_line_number):
return None
copyr = None
m = _CopyrightsScanner._full_copyright_indicator_re.search(line)
if m and \
not _CopyrightsScanner._copyright_disindicator_re.match(m.group(1)):
copyr = m.group(0)
# Prettify the authorship string.
copyr = self.re.sub(r'([,.])?\s*$/', '', copyr)
copyr = self.re.sub(
_CopyrightsScanner._copyright_indicator, '', copyr, \
flags=self.re.IGNORECASE)
copyr = self.re.sub(r'^\s+', '', copyr)
copyr = self.re.sub(r'\s{2,}', ' ', copyr)
copyr = self.re.sub(r'\\@', '@', copyr)
return copyr
def FindCopyrights(input_api, root_dir, files_to_scan):
"""Determines code autorship, and finds generated files.
Args:
input_api: InputAPI, as in presubmit scripts.
root_dir: The root directory, to which all other paths are relative.
files_to_scan: The list of file names to scan.
Returns:
The list of copyrights associated with each of the files given.
If the certain file is generated, the corresponding list consists a single
entry -- 'GENERATED_FILE' string. If the file has no copyright info,
the corresponding list contains 'NO_COPYRIGHT' string.
"""
generated_files_detector = _GeneratedFilesDetector(input_api)
_CopyrightsScanner.StaticInit(input_api)
copyrights = []
for file_name in files_to_scan:
linenum = 0
header = []
file_copyrights = []
scanner = _CopyrightsScanner(input_api)
contents = input_api.ReadFile(
input_api.os_path.join(root_dir, file_name), 'r')
for l in contents.split('\n'):
linenum += 1
if linenum <= 25:
header.append(l)
c = scanner.MatchLine(linenum, l)
if c:
file_copyrights.append(c)
if generated_files_detector.IsGeneratedFile('\n'.join(header)):
copyrights.append([_GeneratedFilesDetector.GENERATED_FILE])
elif file_copyrights:
copyrights.append(file_copyrights)
else:
copyrights.append([_GeneratedFilesDetector.NO_COPYRIGHT])
return copyrights
def FindCopyrightViolations(input_api, root_dir, files_to_scan):
"""Looks for files that are not belong exlusively to the Chromium Authors.
Args:
input_api: InputAPI, as in presubmit scripts.
root_dir: The root directory, to which all other paths are relative.
files_to_scan: The list of file names to scan.
Returns:
The list of file names that contain non-Chromium copyrights.
"""
copyrights = FindCopyrights(input_api, root_dir, files_to_scan)
offending_files = []
allowed_copyrights_re = input_api.re.compile(
r'^(?:20[0-9][0-9](?:-20[0-9][0-9])? The Chromium Authors\. '
'All rights reserved.*)$')
for f, cs in itertools.izip(files_to_scan, copyrights):
if cs[0] == _GeneratedFilesDetector.GENERATED_FILE or \
cs[0] == _GeneratedFilesDetector.NO_COPYRIGHT:
continue
for c in cs:
if not allowed_copyrights_re.match(c):
offending_files.append(input_api.os_path.normpath(f))
break
return offending_files
def _GetWhitelistFileName(input_api):
return input_api.os_path.join(
'tools', 'copyright_scanner', 'third_party_files_whitelist.txt')
def _ProcessWhitelistedFilesList(input_api, lines):
whitelisted_files = []
for line in lines:
match = input_api.re.match(r'([^#\s]+)', line)
if match:
whitelisted_files.append(
ForwardSlashesToOsPathSeps(input_api, match.group(1)))
return whitelisted_files
def LoadWhitelistedFilesList(input_api):
"""Loads and parses the 3rd party code whitelist file.
input_api: InputAPI of presubmit scripts.
Returns:
The list of files.
"""
full_file_name = input_api.os_path.join(
input_api.change.RepositoryRoot(), _GetWhitelistFileName(input_api))
file_data = input_api.ReadFile(full_file_name, 'rb')
return _ProcessWhitelistedFilesList(input_api, file_data.splitlines())
def AnalyzeScanResults(input_api, whitelisted_files, offending_files):
"""Compares whitelist contents with the results of file scanning.
input_api: InputAPI of presubmit scripts.
whitelisted_files: Whitelisted files list.
offending_files: Files that contain 3rd party code.
Returns:
A triplet of "unknown", "missing", and "stale" file lists.
"Unknown" are files that contain 3rd party code but not whitelisted.
"Missing" are files that are whitelisted but doesn't really exist.
"Stale" are files that are whitelisted unnecessarily.
"""
unknown = set(offending_files) - set(whitelisted_files)
missing = [f for f in whitelisted_files if not input_api.os_path.isfile(
input_api.os_path.join(input_api.change.RepositoryRoot(), f))]
stale = set(whitelisted_files) - set(offending_files) - set(missing)
return (list(unknown), missing, list(stale))
def _GetDeletedContents(affected_file):
"""Returns a list of all deleted lines.
AffectedFile class from presubmit_support is lacking this functionality.
"""
deleted_lines = []
for line in affected_file.GenerateScmDiff().splitlines():
if line.startswith('-') and not line.startswith('--'):
deleted_lines.append(line[1:])
return deleted_lines
def _DoScanAtPresubmit(input_api, whitelisted_files, files_to_check):
# We pass empty 'known third-party' dirs list here. Since this is a patch
# for the Chromium's src tree, it must contain properly licensed Chromium
# code. Any third-party code must be put into a directory named 'third_party',
# and such dirs are automatically excluded by FindFiles.
files_to_scan = FindFiles(
input_api, input_api.change.RepositoryRoot(), files_to_check, [])
offending_files = FindCopyrightViolations(
input_api, input_api.change.RepositoryRoot(), files_to_scan)
return AnalyzeScanResults(
input_api, whitelisted_files, offending_files)
def ScanAtPresubmit(input_api, output_api):
"""Invoked at change presubmit time. Verifies that updated non third-party
code doesn't contain external copyrighted code.
input_api: InputAPI of presubmit scripts.
output_api: OutputAPI of presubmit scripts.
"""
files_to_check = set([])
deleted_files = set([])
whitelist_contents_changed = False
for f in input_api.AffectedFiles():
if f.LocalPath() == _GetWhitelistFileName(input_api):
whitelist_contents_changed = True
deleted_files |= set(_ProcessWhitelistedFilesList(
input_api, _GetDeletedContents(f)))
continue
if f.Action() != 'D':
files_to_check.add(f.LocalPath())
else:
deleted_files.add(f.LocalPath())
whitelisted_files = set(LoadWhitelistedFilesList(input_api))
if not whitelist_contents_changed:
whitelisted_files &= files_to_check | deleted_files
else:
# Need to re-check the entire contents of the whitelist file.
# Also add files removed from the whitelist. If the file has indeed been
# deleted, the scanner will not complain.
files_to_check |= whitelisted_files | deleted_files
(unknown_files, missing_files, stale_files) = _DoScanAtPresubmit(
input_api, list(whitelisted_files), list(files_to_check))
results = []
if unknown_files:
results.append(output_api.PresubmitError(
'The following files contain a third-party license but are not in ' \
'a listed third-party directory and are not whitelisted. You must ' \
'add the following files to the whitelist file %s\n' \
'(Note that if the code you are adding does not actually contain ' \
'any third-party code, it may contain the word "copyright", which ' \
'should be masked out, e.g. by writing it as "copy-right"):' \
'' % _GetWhitelistFileName(input_api),
sorted(unknown_files)))
if missing_files:
results.append(output_api.PresubmitPromptWarning(
'The following files are whitelisted in %s, ' \
'but do not exist or not files:' % _GetWhitelistFileName(input_api),
sorted(missing_files)))
if stale_files:
results.append(output_api.PresubmitPromptWarning(
'The following files are whitelisted unnecessarily. You must ' \
'remove the following files from the whitelist file ' \
'%s:' % _GetWhitelistFileName(input_api),
sorted(stale_files)))
return results
#!/usr/bin/env python
# Copyright 2014 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
"""Unit tests for Copyright Scanner utilities."""
import os
import re
import sys
import unittest
test_dir = os.path.dirname(os.path.abspath(__file__))
sys.path.extend([
os.path.normpath(os.path.join(test_dir, '..', '..', 'build')),
os.path.join(test_dir),
])
import find_depot_tools
from testing_support.super_mox import SuperMoxTestBase
import copyright_scanner
class FindCopyrightsTest(SuperMoxTestBase):
def setUp(self):
SuperMoxTestBase.setUp(self)
self.input_api = self.mox.CreateMockAnything()
self.input_api.re = re
self.input_api.os_path = os.path
self.input_api.os_walk = os.walk
def ShouldMatchReferenceOutput(self, test_data, expected_output):
for data in test_data:
self.input_api.ReadFile = lambda _1, _2: data
actual_output = copyright_scanner.FindCopyrights(self.input_api, '', [''])
self.assertEqual(
expected_output,
actual_output,
'Input """\n%s""", expected output: "%s", actual: "%s"' % \
(data, expected_output, actual_output));
def testCopyrightedFiles(self):
test_data = [
'// (c) 2014 Google Inc.\n//\n// (a) One\n//\n// (b) Two\n//\n',
'Copyright 2014 Google Inc.\n',
'Copr. 2014 Google Inc.',
'\xc2\xa9 2014 Google Inc.',
'Copyright 2014 Google Inc.'
]
self.ShouldMatchReferenceOutput(test_data, [['2014 Google Inc.']])
def testGeneratedFiles(self):
test_data = [
'ALL CHANGES MADE IN THIS FILE WILL BE LOST\nCopyright 2014 Google\n',
'GENERATED FILE. DO NOT EDIT\nCopyright 2014 Google\n',
'GENERATED. DO NOT DELETE THIS FILE.\nCopyright 2014 Google\n',
'DO NOT EDIT\nCopyright 2014 Google\n',
'DO NOT DELETE THIS FILE\nCopyright 2014 Google\n',
'All changes made in this file will be lost\nCopyright 2014 Google\n',
'Automatically generated file\nCopyright 2014 Google\n',
'Synthetically generated dummy file\nCopyright 2014 Google\n',
'Generated data (by gnugnu)\nCopyright 2014 Google\n'
]
self.ShouldMatchReferenceOutput(test_data, [['GENERATED FILE']])
def testNonCopyrightedFiles(self):
test_data = [
'std::cout << "Copyright 2014 Google"\n',
'// Several points can be made:\n//\n// (a) One\n//\n// (b) Two\n'
'//\n// (c) Three\n//\n',
'See \'foo\' for copyright information.\n',
'See \'foo\' for the copyright notice.\n',
'See \'foo\' for the copyright and other things.\n'
]
self.ShouldMatchReferenceOutput(test_data, [['*No copyright*']])
def testNonGeneratedFiles(self):
test_data = [
'This file was prohibited from being generated.\n',
'Please do not delete our files! They are valuable to us.\n',
'Manually generated from dice rolls.\n',
'"""This Python script produces generated data\n"""\n',
'\'\'\'This Python script produces generated data\n\'\'\'\n'
]
self.ShouldMatchReferenceOutput(test_data, [['*No copyright*']])
class FindFilesTest(SuperMoxTestBase):
def setUp(self):
SuperMoxTestBase.setUp(self)
self.input_api = self.mox.CreateMockAnything()
self.input_api.re = re
self.input_api.os_path = os.path
def testFilesAsStartPaths(self):
join = self.input_api.os_path.join
self.input_api.os_path.isfile = lambda _: True
input_files = [
'a',
'a.cc',
'a.txt',
join('foo', 'a'),
join('foo', 'a.cc'),
join('foo', 'a.txt'),
join('third_party', 'a'),
join('third_party', 'a.cc'),
join('third_party', 'a.txt'),
join('foo', 'third_party', 'a'),
join('foo', 'third_party', 'a.cc'),
join('foo', 'third_party', 'a.txt'),
]
root_dir = os.path.sep + 'src'
actual = copyright_scanner.FindFiles(
self.input_api, root_dir, input_files, [''])
self.assertEqual(['a.cc', join('foo', 'a.cc')], actual)
actual = copyright_scanner.FindFiles(
self.input_api, root_dir, input_files, ['third_party'])
self.assertEqual(['a.cc', join('foo', 'a.cc')], actual)
actual = copyright_scanner.FindFiles(
self.input_api, root_dir, input_files, ['foo'])
self.assertEqual(['a.cc'], actual)
actual = copyright_scanner.FindFiles(
self.input_api, root_dir, input_files, ['foo', 'third_party'])
self.assertEqual(['a.cc'], actual)
actual = copyright_scanner.FindFiles(
self.input_api, root_dir, input_files, [join('foo', 'third_party')])
self.assertEqual(['a.cc', join('foo', 'a.cc')], actual)
def testDirAsStartPath(self):
self.input_api.os_path.isfile = lambda _: False
join = self.input_api.os_path.join
normpath = self.input_api.os_path.normpath
root_dir = os.path.sep + 'src'
scan_from = '.'
base_path = join(root_dir, scan_from)
def mock_os_walk(path):
return lambda _: [(join(base_path, path), [''], ['a', 'a.cc', 'a.txt'])]
self.input_api.os_walk = mock_os_walk('')
actual = map(normpath, copyright_scanner.FindFiles(
self.input_api, root_dir, [scan_from], ['']))
self.assertEqual(['a.cc'], actual)
self.input_api.os_walk = mock_os_walk('third_party')
actual = map(normpath, copyright_scanner.FindFiles(
self.input_api, root_dir, [scan_from], ['']))
self.assertEqual([], actual)
self.input_api.os_walk = mock_os_walk('foo')
actual = map(normpath, copyright_scanner.FindFiles(
self.input_api, root_dir, [scan_from], ['']))
self.assertEqual([join('foo', 'a.cc')], actual)
self.input_api.os_walk = mock_os_walk('foo')
actual = map(normpath, copyright_scanner.FindFiles(
self.input_api, root_dir, [scan_from], ['foo']))
self.assertEqual([], actual)
self.input_api.os_walk = mock_os_walk(join('foo', 'bar'))
actual = map(normpath, copyright_scanner.FindFiles(
self.input_api, root_dir, [scan_from], ['foo']))
self.assertEqual([], actual)
self.input_api.os_walk = mock_os_walk(join('foo', 'third_party'))
actual = map(normpath, copyright_scanner.FindFiles(
self.input_api, root_dir, [scan_from], ['']))
self.assertEqual([], actual)
self.input_api.os_walk = mock_os_walk(join('foo', 'third_party'))
actual = map(normpath, copyright_scanner.FindFiles(
self.input_api, root_dir, [scan_from], [join('foo', 'third_party')]))
self.assertEqual([], actual)
class AnalyzeScanResultsTest(SuperMoxTestBase):
def setUp(self):
SuperMoxTestBase.setUp(self)
self.input_api = self.mox.CreateMockAnything()
self.input_api.os_path = os.path
self.input_api.change = self.mox.CreateMockAnything()
self.input_api.change.RepositoryRoot = lambda: ''
def testAnalyzeScanResults(self):
# Tests whitelisted vs. current files state logic.
#
# Whitelisted - in whitelist, and contains 3rd party code => OK
# Missing - in whitelist, but doesn't exist
# Stale - in whitelist, but is clean
# Unknown - not in whitelist, but contains 3rd party code
self.input_api.os_path.isfile = lambda x: x != 'Missing'
self.assertEqual(
(['Unknown'], ['Missing'], ['Stale']),
copyright_scanner.AnalyzeScanResults(self.input_api, \
['Whitelisted', 'Missing', 'Stale'], ['Whitelisted', 'Unknown']))
class ScanAtPresubmitTest(SuperMoxTestBase):
def setUp(self):
SuperMoxTestBase.setUp(self)
self.input_api = self.mox.CreateMockAnything()
self.input_api.re = re
self.input_api.os_path = os.path
self.output_api = self.mox.CreateMockAnything()
def tearDown(self):
self.mox.UnsetStubs()
SuperMoxTestBase.tearDown(self)
class AffectedFileMock(object):
def __init__(self, local_path, action):
self._local_path = local_path
self._action = action
def LocalPath(self):
return self._local_path
def Action(self):
return self._action
def CreateAffectedFilesFunc(self, paths_and_actions):
result = []
for i in range(0, len(paths_and_actions), 2):
result.append(ScanAtPresubmitTest.AffectedFileMock(
paths_and_actions[i], paths_and_actions[i + 1]))
return lambda: result
def CreateDoScanAtPresubmitFunc(self):
self._whitelisted_files = None
self._files_to_check = None
def ScanAtPresubmitStub(_, whitelisted, to_check):
self._whitelisted_files = whitelisted
self._files_to_check = to_check
return ([], [], [])
return ScanAtPresubmitStub
def GetWhitelistedFiles(self):
return sorted(self._whitelisted_files)
def GetFilesToCheck(self):
return sorted(self._files_to_check)
def testWhitelistedUntouched(self):
# When a change doesn't touch the whitelist file, any updated files
# (except deleted) must be checked. The whitelist used for analysis
# must be trimmed to the changed files subset.
#
# A_NW.cc - added, not whitelisted => check
# A_W.cc - added, whitelisted => check, remain on the trimmed whitelist
# D_NW.cc - deleted, not whitelisted => ignore
# D_W.cc - deleted and whitelisted => remain on w/l
# M_NW.cc - modified, not whitelisted => check
# M_W.cc - modified and whitelisted => check, remain on w/l
# NM_W.cc - not modified, whitelisted => trim from w/l
# W - the whitelist file
self.input_api.AffectedFiles = self.CreateAffectedFilesFunc(
['A_NW.cc', 'A', 'A_W.cc', 'A', 'D_NW.cc', 'D', 'D_W.cc', 'D',
'M_NW.cc', 'M', 'M_W.cc', 'M'])
self.mox.StubOutWithMock(copyright_scanner, '_GetWhitelistFileName')
copyright_scanner._GetWhitelistFileName = lambda _: 'W'
self.mox.StubOutWithMock(copyright_scanner, 'LoadWhitelistedFilesList')
copyright_scanner.LoadWhitelistedFilesList = \
lambda _: ['A_W.cc', 'D_W.cc', 'M_W.cc', 'NM_W.cc']
self.mox.StubOutWithMock(copyright_scanner, '_DoScanAtPresubmit')
copyright_scanner._DoScanAtPresubmit = self.CreateDoScanAtPresubmitFunc()
self.mox.ReplayAll()
copyright_scanner.ScanAtPresubmit(self.input_api, self.output_api)
self.assertEqual(
['A_W.cc', 'D_W.cc', 'M_W.cc'], self.GetWhitelistedFiles())
self.assertEqual(
['A_NW.cc', 'A_W.cc', 'M_NW.cc', 'M_W.cc'], self.GetFilesToCheck())
def testWhitelistTouched(self):
# When the whitelist file is touched by the change, all the files listed in
# it, including deleted entries, must be re-checked. All modified files
# (including the deleted ones) must be checked as well. The current contents
# of the whitelist are used for analysis.
# Whitelist addition or deletion are not considered.
#
# All the files from names testWhitelistedUntouched are re-used, but now
# action for all of them is 'check' (except for the w/l file itself).
# A_DW.cc - added, deleted from w/l => check
# D_DW.cc - deleted from repo and w/l => check
# M_DW.cc - modified, deleted from w/l => check
self.input_api.AffectedFiles = self.CreateAffectedFilesFunc(
['A_DW.cc', 'A', 'A_NW.cc', 'A', 'A_W.cc', 'A',
'D_DW.cc', 'D', 'D_NW.cc', 'D', 'D_W.cc', 'D',
'M_DW.cc', 'M', 'M_NW.cc', 'M', 'M_W.cc', 'M', 'W', 'M'])
self.mox.StubOutWithMock(copyright_scanner, '_GetWhitelistFileName')
copyright_scanner._GetWhitelistFileName = lambda _: 'W'
self.mox.StubOutWithMock(copyright_scanner, '_GetDeletedContents')
def GetDeletedContentsStub(affected_file):
self.assertEqual('W', affected_file.LocalPath())
return ['A_DW.cc', 'D_DW.cc', 'M_DW.cc']
copyright_scanner._GetDeletedContents = GetDeletedContentsStub
self.mox.StubOutWithMock(copyright_scanner, 'LoadWhitelistedFilesList')
copyright_scanner.LoadWhitelistedFilesList = \
lambda _: ['A_W.cc', 'D_W.cc', 'M_W.cc', 'NM_W.cc']
self.mox.StubOutWithMock(copyright_scanner, '_DoScanAtPresubmit')
copyright_scanner._DoScanAtPresubmit = self.CreateDoScanAtPresubmitFunc()
self.mox.ReplayAll()
copyright_scanner.ScanAtPresubmit(self.input_api, self.output_api)
self.assertEqual(
['A_W.cc', 'D_W.cc', 'M_W.cc', 'NM_W.cc'], self.GetWhitelistedFiles())
self.assertEqual(
['A_DW.cc', 'A_NW.cc', 'A_W.cc', 'D_DW.cc', 'D_NW.cc', 'D_W.cc',
'M_DW.cc', 'M_NW.cc', 'M_W.cc', 'NM_W.cc' ], self.GetFilesToCheck())
if __name__ == '__main__':
unittest.main()
# Copyright (c) 2012 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
# This file records third-party licensing information for the purposes of the
# Android WebView build. See webview_licenses.py for details.
#
# New third-party code should be added under a directory named 'third_party',
# so additions to this file should be rare. See
# http://www.chromium.org/developers/adding-3rd-party-libraries.
#
# Please always use forward slashes '/' as path separators, even if you are
# on Windows.
# Copyright IBM; MIT license. This third-party code is taken from ICU, the
# license for which we already pick up from third_party/icu/.
base/i18n/icu_string_conversions.cc
# Contains '(c)' in comments
base/logging.h
# Copyright Ron Rivest, public domain.
base/md5.cc
# Copyright Apple Inc; BSD license. Moved from third_party/WebKit/.
cc/input/scroll_elasticity_helper.h
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/browser/importer/firefox_profile_lock.cc
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/browser/importer/firefox_profile_lock.h
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/browser/importer/firefox_profile_lock_posix.cc
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/browser/importer/firefox_profile_lock_win.cc
# String 'copyright' used in code.
chrome/common/importer/firefox_importer_utils.cc
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/utility/importer/nss_decryptor.cc
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/utility/importer/nss_decryptor_mac.h
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/utility/importer/nss_decryptor_system_nss.cc
# Copyright Netscape Communications Corporation; MPL, GPL v2 or LGPL v2
# license. Not used on Android.
chrome/utility/importer/nss_decryptor_win.h
# Copyright Google Inc; BSD license. Test code only.
chrome/tools/test/generate_mime_tests.pl
# String 'copyright' used in the text presented to the user as part of
# Google Chrome terms of service.
components/resources/terms/chromeos/terms_en.html
components/resources/terms/terms_am.html
components/resources/terms/terms_ca.html
components/resources/terms/terms_cs.html
components/resources/terms/terms_da.html
components/resources/terms/terms_de.html
components/resources/terms/terms_en-GB.html
components/resources/terms/terms_en.html
components/resources/terms/terms_es-419.html
components/resources/terms/terms_es.html
components/resources/terms/terms_et.html
components/resources/terms/terms_fi.html
components/resources/terms/terms_fil.html
components/resources/terms/terms_fr.html
components/resources/terms/terms_he.html
components/resources/terms/terms_hr.html
components/resources/terms/terms_hu.html
components/resources/terms/terms_id.html
components/resources/terms/terms_it.html
components/resources/terms/terms_ja.html
components/resources/terms/terms_kn.html
components/resources/terms/terms_ko.html
components/resources/terms/terms_lt.html
components/resources/terms/terms_lv.html
components/resources/terms/terms_ml.html
components/resources/terms/terms_nb.html
components/resources/terms/terms_nl.html
components/resources/terms/terms_pl.html
components/resources/terms/terms_pt-BR.html
components/resources/terms/terms_pt-PT.html
components/resources/terms/terms_ro.html
components/resources/terms/terms_sk.html
components/resources/terms/terms_sl.html
components/resources/terms/terms_sr.html
components/resources/terms/terms_sv.html
components/resources/terms/terms_sw.html
components/resources/terms/terms_ta.html
components/resources/terms/terms_te.html
components/resources/terms/terms_th.html
components/resources/terms/terms_tr.html
components/resources/terms/terms_vi.html
# Copyright Apple Inc, Nokia Corporation and Torch Mobile Inc; BSD license.
# Contains code moved from third_party/WebKit/.
content/browser/frame_host/navigation_controller_impl.cc
# Copyright Apple, Inc, Google Inc; BSD license. Not used on Android.
# Moved from third_party/WebKit/.
content/browser/renderer_host/input/web_input_event_builders_mac.mm
# Copyright Apple Inc and Torch Mobile Inc; BSD license. Moved from
# third_party/WebKit/.
content/renderer/history_controller.h
# Copyright Apple Inc, Nokia Corporation and Torch Mobile Inc; BSD license.
# Moved from third_party/WebKit/.
content/renderer/history_controller.cc
# Copyright Apple Inc and Torch Mobile Inc; BSD license. Moved from
# third_party/WebKit/.
content/renderer/history_entry.h
# Copyright Apple Inc, Nokia Corporation and Torch Mobile Inc; BSD license.
# Moved from third_party/WebKit/.
content/renderer/history_entry.cc
# Copyright Google Inc, no license. Not used on Android.
google_update/google_update_idl.idl
# Copyright WebM Project authors; BSD license. Copied and modified from
# third_party/libvpx. Not used on Android.
media/filters/vp8_bool_decoder.h
media/filters/vp8_bool_decoder.cc
# Native client not used in Android. Contains the word "Copyright"
native_client_sdk/doc_generated/rest-devsite-examples.html
# String '(c)' used in certificates organization names
net/cert/x509_certificate_known_roots_win.h
net/quic/core/crypto/common_cert_set_2a.inc
net/quic/core/crypto/common_cert_set_2b.inc
net/quic/core/crypto/common_cert_set_3a.inc
net/quic/core/crypto/common_cert_set_3b.inc
# String '(c)' used in certificates organization names
net/test/test_certificate_data.h
# Copyright The Chromium Authors and Netscape Communications Corporation; BSD
# and (MPL, GPL v2 or LGPL v2) licenses. This third-party code is taken from
# Mozilla, the license for which we already pick up from third_party/npapi/.
net/cookies/cookie_monster.cc
# Copyright The Chromium Authors and Netscape Communications Corporation; BSD
# and (MPL, GPL v2 or LGPL v2) licenses. This third-party code is taken from
# Mozilla, the license for which we already pick up from third_party/npapi/.
net/cookies/canonical_cookie.cc
# Copyright The Chromium Authors and Netscape Communications Corporation; BSD
# and (MPL, GPL v2 or LGPL v2) licenses. This third-party code is taken from
# Mozilla, the license for which we already pick up from third_party/npapi/.
net/cookies/parsed_cookie.cc
# Copyright The Chromium Authors and Google Inc; BSD and (MPL, GPL v2 or LGPL
# v2) licenses. This third-party code is taken from Mozilla, the license for
# which we already pick up from third_party/npapi/.
net/base/registry_controlled_domains/registry_controlled_domain.cc
# Copyright The Chromium Authors and Google Inc; BSD and (MPL, GPL v2 or LGPL
# v2) licenses. This third-party code is taken from Mozilla, the license for
# which we already pick up from third_party/npapi/.
net/base/registry_controlled_domains/registry_controlled_domain.h
# Copyright The Chromium Authors and IBM Corporation; BSD and (MPL, GPL v2 or
# LGPL v2) licenses. This third-party code is taken from Mozilla, the license
# for which we already pick up from third_party/npapi/.
net/http/des.cc
# Copyright The Chromium Authors and IBM Corporation; BSD and (MPL, GPL v2 or
# LGPL v2) licenses. This third-party code is taken from Mozilla, the license
# for which we already pick up from third_party/npapi/.
net/http/http_auth_handler_ntlm_portable.cc
# Copyright The Chromium Authors and Netscape Communications; BSD and (MPL, GPL
# v2 or LGPL v2) licenses. This third-party code is taken from Mozilla, the
# license for which we already pick up from third_party/npapi/.
net/http/http_chunked_decoder.cc
# Copyright The Chromium Authors and Netscape Communications; BSD and (MPL, GPL
# v2 or LGPL v2) licenses. This third-party code is taken from Mozilla, the
# license for which we already pick up from third_party/npapi/.
net/http/http_chunked_decoder.h
# Copyright IBM Corporation; MPL, GPL v2 or LGPL v2 license. This third-party
# code is taken from Mozilla, the license for which we already pick up from
# third_party/npapi/.
net/http/md4.cc
# Copyright IBM Corporation; MPL, GPL v2 or LGPL v2 license. This third-party
# code is taken from Mozilla, the license for which we already pick up from
# third_party/npapi/.
net/http/md4.h
# Netscape Communications Corporation; MPL, GPL v2 or LGPL v2 license. This
# third-party code is taken from Mozilla, the license for which we already pick
# up from third_party/npapi/.
net/proxy/proxy_resolver_script.h
# Contains the word 'Copyright' in comments
ppapi/generators/idl_c_proto.py
ppapi/generators/idl_outfile.py
# Copyright (c) 2007-2009 The Khronos Group Inc. Not used on Android
ppapi/lib/gl/include/EGL/egl.h
ppapi/lib/gl/include/EGL/eglext.h
ppapi/lib/gl/include/EGL/eglplatform.h
ppapi/lib/gl/include/KHR/khrplatform.h
# Copyright The Android Open Source Project; ASL v2 license.
skia/config/SkUserConfig.h
# Generates copyright headers for Chromium.
tools/boilerplate.py
# Contains test strings that look like copyrights.
tools/copyright_scanner/copyright_scanner_unittest.py
# Contains word 'copyright' in comments.
tools/gen_keyboard_overlay_data/gen_keyboard_overlay_data.py
# This third-party code is taken from Mozilla, but is copyright Google and has
# been re-licensed under the Chromium license.
tools/imagediff/image_diff_png.cc
# Copyright Ero Carrera; BSD license. Tool only.
tools/symsrc/pefile.py
# Copyright The Chromium Authors, Sun Microsystems Inc, the V8 project authors;
# BSD license. Tool only.
tools/traceline/traceline/assembler.h
# Copyright Google Inc; BSD license. Tool only.
tools/traceline/traceline/sidestep/mini_disassembler.cc
# Copyright Marijn Haverbeke. MIT license. Tool only, not used on Android.
tools/win/sizeviewer/clike.js
# Copyright Marijn Haverbeke. MIT license. Tool only, not used on Android.
tools/win/sizeviewer/codemirror.js
# Copyright The Chromium Authors, Apple Inc; BSD license. Not used on Android.
ui/base/clipboard/clipboard_util_win.cc
# Copyright The Chromium Authors, Apple Inc and Graham Dennis; BSD license. Not
# used on Android.
ui/base/cocoa/tool_tip_base_view.mm
# Copyright The Chromium Authors, Apple Inc; BSD license. Not used on Android.
ui/base/dragdrop/os_exchange_data_provider_win.cc
# Copyright Apple Inc; BSD license. Moved from third_party/WebKit/.
ui/events/blink/input_scroll_elasticity_controller.cc
ui/events/blink/input_scroll_elasticity_controller.h
# Copyright The Chromium Authors, Michael Emmel, Google Inc; BSD license. This
# third-party code is taken from WebKit, the license for which we already pick
# up from webkit/.
ui/events/keycodes/keyboard_codes_posix.h
# String 'copyright' used in code.
ui/file_manager/file_manager/foreground/js/main_scripts.js
# String 'copyright' used in code.
ui/file_manager/gallery/js/gallery_scripts.js
# String 'copyright' used in code.
ui/file_manager/video_player/js/video_player_scripts.js
# This third-party code is taken from Mozilla, but is copyright Google and has
# been re-licensed under the Chromium license.
ui/gfx/codec/jpeg_codec.cc
# This third-party code is taken from Mozilla, but is copyright Google and has
# been re-licensed under the Chromium license.
ui/gfx/codec/png_codec.cc
# Copyright The Chromium Authors and Apple Inc; BSD license. This third-party
# code is taken from WebKit, the license for which we already pick up from
# webkit/.
content/browser/appcache/appcache_manifest_parser.cc
# Copyright The Chromium Authors and Apple Inc; BSD license. This third-party
# code is taken from WebKit, the license for which we already pick up from
# webkit/.
content/browser/appcache/appcache_manifest_parser.h
# String 'copyright' used in code.
ui/webui/resources/js/cr/ui/array_data_model.js
# Bundles of existing code.
chrome/browser/resources/md_downloads/vulcanized.html
chrome/browser/resources/md_history/app.vulcanized.html
chrome/browser/resources/md_history/lazy_load.vulcanized.html
# Generated config files, which are checked in outside of the third-party
# library they configure. Copyright The open-vcdiff Authors; Apache2 license.
sdch/ios/config.h
sdch/linux/config.h
sdch/mac/config.h
sdch/win/config.h
per-file licenses_test.py=file://tools/copyright_scanner/OWNERS per-file licenses_test.py=phajdan.jr@chromium.org
per-file licenses_test.py=sgurun@chromium.org
per-file licenses_test.py=torne@chromium.org
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment