2012-08-22 18:10:37 +00:00
|
|
|
#!/usr/bin/env python
|
|
|
|
# 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.
|
|
|
|
|
2021-03-25 13:04:43 +00:00
|
|
|
|
2012-08-22 18:10:37 +00:00
|
|
|
"""Module that sanitizes source files with specified modifiers."""
|
|
|
|
|
|
|
|
|
2021-03-25 13:04:43 +00:00
|
|
|
from __future__ import print_function
|
2012-08-22 18:10:37 +00:00
|
|
|
import commands
|
|
|
|
import os
|
|
|
|
import sys
|
|
|
|
|
|
|
|
|
2017-02-06 17:26:51 +00:00
|
|
|
_FILE_EXTENSIONS_TO_SANITIZE = ['cpp', 'h', 'c']
|
2012-08-22 18:10:37 +00:00
|
|
|
|
2013-09-11 13:01:27 +00:00
|
|
|
_SUBDIRS_TO_IGNORE = ['.git', '.svn', 'third_party']
|
2012-08-22 18:10:37 +00:00
|
|
|
|
|
|
|
|
|
|
|
def SanitizeFilesWithModifiers(directory, file_modifiers, line_modifiers):
|
|
|
|
"""Sanitizes source files with the specified file and line modifiers.
|
|
|
|
|
|
|
|
Args:
|
|
|
|
directory: string - The directory which will be recursively traversed to
|
|
|
|
find source files to apply modifiers to.
|
|
|
|
file_modifiers: list - file-modification methods which should be applied to
|
2013-01-25 18:26:58 +00:00
|
|
|
the complete file content (Eg: EOFOneAndOnlyOneNewlineAdder).
|
2012-08-22 18:10:37 +00:00
|
|
|
line_modifiers: list - line-modification methods which should be applied to
|
|
|
|
lines in a file (Eg: TabReplacer).
|
|
|
|
"""
|
|
|
|
for item in os.listdir(directory):
|
|
|
|
|
|
|
|
full_item_path = os.path.join(directory, item)
|
|
|
|
|
|
|
|
if os.path.isfile(full_item_path): # Item is a file.
|
|
|
|
|
|
|
|
# Only sanitize files with extensions we care about.
|
|
|
|
if (len(full_item_path.split('.')) > 1 and
|
|
|
|
full_item_path.split('.')[-1] in _FILE_EXTENSIONS_TO_SANITIZE):
|
|
|
|
f = file(full_item_path)
|
|
|
|
try:
|
|
|
|
lines = f.readlines()
|
|
|
|
finally:
|
|
|
|
f.close()
|
|
|
|
|
|
|
|
new_lines = [] # Collect changed lines here.
|
|
|
|
line_number = 0 # Keeps track of line numbers in the source file.
|
|
|
|
write_to_file = False # File is written to only if this flag is set.
|
|
|
|
|
|
|
|
# Run the line modifiers for each line in this file.
|
|
|
|
for line in lines:
|
|
|
|
original_line = line
|
|
|
|
line_number += 1
|
|
|
|
|
|
|
|
for modifier in line_modifiers:
|
|
|
|
line = modifier(line, full_item_path, line_number)
|
|
|
|
if original_line != line:
|
|
|
|
write_to_file = True
|
|
|
|
new_lines.append(line)
|
|
|
|
|
|
|
|
# Run the file modifiers.
|
|
|
|
old_content = ''.join(lines)
|
|
|
|
new_content = ''.join(new_lines)
|
|
|
|
for modifier in file_modifiers:
|
|
|
|
new_content = modifier(new_content, full_item_path)
|
|
|
|
if new_content != old_content:
|
|
|
|
write_to_file = True
|
|
|
|
|
|
|
|
# Write modifications to the file.
|
|
|
|
if write_to_file:
|
|
|
|
f = file(full_item_path, 'w')
|
|
|
|
try:
|
|
|
|
f.write(new_content)
|
|
|
|
finally:
|
|
|
|
f.close()
|
2021-03-25 13:04:43 +00:00
|
|
|
print('Made changes to %s' % full_item_path)
|
2012-08-22 18:10:37 +00:00
|
|
|
|
|
|
|
elif item not in _SUBDIRS_TO_IGNORE:
|
|
|
|
# Item is a directory recursively call the method.
|
|
|
|
SanitizeFilesWithModifiers(full_item_path, file_modifiers, line_modifiers)
|
|
|
|
|
|
|
|
|
|
|
|
############## Line Modification methods ##############
|
|
|
|
|
|
|
|
|
|
|
|
def TrailingWhitespaceRemover(line, file_path, line_number):
|
|
|
|
"""Strips out trailing whitespaces from the specified line."""
|
|
|
|
stripped_line = line.rstrip() + '\n'
|
|
|
|
if line != stripped_line:
|
2021-03-25 13:04:43 +00:00
|
|
|
print('Removing trailing whitespace in %s:%s' % (file_path, line_number))
|
2012-08-22 18:10:37 +00:00
|
|
|
return stripped_line
|
|
|
|
|
|
|
|
|
|
|
|
def CrlfReplacer(line, file_path, line_number):
|
|
|
|
"""Replaces CRLF with LF."""
|
|
|
|
if '\r\n' in line:
|
2021-03-25 13:04:43 +00:00
|
|
|
print('Replacing CRLF with LF in %s:%s' % (file_path, line_number))
|
2012-08-22 18:10:37 +00:00
|
|
|
return line.replace('\r\n', '\n')
|
|
|
|
|
|
|
|
|
|
|
|
def TabReplacer(line, file_path, line_number):
|
|
|
|
"""Replaces Tabs with 4 whitespaces."""
|
|
|
|
if '\t' in line:
|
2021-03-25 13:04:43 +00:00
|
|
|
print('Replacing Tab with whitespace in %s:%s' % (file_path, line_number))
|
2012-08-22 18:10:37 +00:00
|
|
|
return line.replace('\t', ' ')
|
|
|
|
|
|
|
|
|
|
|
|
############## File Modification methods ##############
|
|
|
|
|
|
|
|
|
|
|
|
def CopywriteChecker(file_content, unused_file_path):
|
|
|
|
"""Ensures that the copywrite information is correct."""
|
|
|
|
# TODO(rmistry): Figure out the legal implications of changing old copyright
|
|
|
|
# headers.
|
|
|
|
return file_content
|
|
|
|
|
|
|
|
|
2013-01-25 18:26:58 +00:00
|
|
|
def EOFOneAndOnlyOneNewlineAdder(file_content, file_path):
|
|
|
|
"""Adds one and only one LF at the end of the file."""
|
|
|
|
if file_content and (file_content[-1] != '\n' or file_content[-2:-1] == '\n'):
|
|
|
|
file_content = file_content.rstrip()
|
2012-08-22 18:10:37 +00:00
|
|
|
file_content += '\n'
|
2021-03-25 13:04:43 +00:00
|
|
|
print('Added exactly one newline to %s' % file_path)
|
2012-08-22 18:10:37 +00:00
|
|
|
return file_content
|
|
|
|
|
|
|
|
|
|
|
|
def SvnEOLChecker(file_content, file_path):
|
|
|
|
"""Sets svn:eol-style property to LF."""
|
|
|
|
output = commands.getoutput(
|
|
|
|
'svn propget svn:eol-style %s' % file_path)
|
|
|
|
if output != 'LF':
|
2021-03-25 13:04:43 +00:00
|
|
|
print('Setting svn:eol-style property to LF in %s' % file_path)
|
2012-08-22 18:10:37 +00:00
|
|
|
os.system('svn ps svn:eol-style LF %s' % file_path)
|
|
|
|
return file_content
|
|
|
|
|
|
|
|
|
|
|
|
#######################################################
|
|
|
|
|
|
|
|
|
|
|
|
if '__main__' == __name__:
|
|
|
|
sys.exit(SanitizeFilesWithModifiers(
|
|
|
|
os.getcwd(),
|
|
|
|
file_modifiers=[
|
|
|
|
CopywriteChecker,
|
2013-01-25 18:26:58 +00:00
|
|
|
EOFOneAndOnlyOneNewlineAdder,
|
2012-08-22 18:10:37 +00:00
|
|
|
SvnEOLChecker,
|
|
|
|
],
|
|
|
|
line_modifiers=[
|
|
|
|
CrlfReplacer,
|
|
|
|
TabReplacer,
|
|
|
|
TrailingWhitespaceRemover,
|
|
|
|
],
|
|
|
|
))
|