1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109
|
# Fill out block comments to the full line length (currently 100).
#
# We're defining a "block comment" to be a multiline comment where each line
# begins with an alphabetic character.
#
# We also have some special logic to handle function description comments even
# though those don't conform to our definition of a "block comment".
import re, sys
# List of words in the current block comment.
words = []
# Whether we're inside a potential block comment.
multiline = False
# The maximum allowed line length.
line_length = 100
# How far to indent the current block comment.
indentation = 0
# Whether we're inside a function description comment. This is not a block
# comment by our definition but we want to fill these too.
function_desc = False
# Whether we've seen a line in the multiline comment to indicate that it is NOT
# a block comment. In that case don't use the refilling logic and just print the
# contents verbatim.
block = False
# The literal contents of the current block comment. If we realise halfway
# through the comment that it's not a block comment then we'll just print this
# out and pretend none of this ever happened.
comment = str()
for line in sys.stdin:
sline = line.strip()
# Beginning of a block comment.
if sline == '/*':
comment = line
assert not multiline
multiline = True
block = True
# Figure out how far we need to indent.
indentation = 0
for c in line:
if c == ' ':
indentation += 1
elif c == '\t':
indentation += 8
else:
break
# End of a block comment.
elif sline.endswith('*/'):
comment += line
# Don't mess with generated comments.
# Scripts in dist rely on them to figure out where to generate code.
if 'DO NOT EDIT' in comment:
block = False
if multiline and not block:
sys.stdout.write(comment)
elif multiline:
indent_ws = ' ' * indentation
sys.stdout.write('{}/*\n'.format(indent_ws))
current_line = indent_ws + ' *'
for word in words:
if word == '--' and function_desc:
sys.stdout.write(current_line + ' ' + word + '\n')
current_line = indent_ws + ' *' + ' ' * 4
continue
if word == '\n':
sys.stdout.write(current_line + '\n')
sys.stdout.write(indent_ws + ' *' + '\n')
current_line = indent_ws + ' *'
continue
if len(current_line) + len(word) >= line_length:
sys.stdout.write(current_line + '\n')
current_line = indent_ws + ' *'
if function_desc:
current_line += ' ' * 4
current_line += ' ' + word
sys.stdout.write(current_line + '\n')
sys.stdout.write('{} */\n'.format(indent_ws))
else:
sys.stdout.write(line)
block = False
words = []
multiline = False
function_desc = False
elif multiline:
comment += line
# Function names begin with either a lowercase char or an underscore.
if (len(sline) >= 3 and sline.startswith('*') and sline[1] == ' ' and
(sline[2].islower() or sline[2] == '_') and sline.endswith('--')):
function_desc = True
# We're only reformatting block comments where each line begins with a
# space and an alphabetic character after the asterisk. The only
# exceptions are function descriptions.
block = block and \
(len(sline) >= 3 and sline.startswith('*') and
sline[1] == ' ' and sline[2].isalpha()) or function_desc
# Trim asterisks at the beginning of each line in a multiline comment.
if sline.startswith('*'):
sline = sline[1:]
# Might be trailing whitespace after the asterisk. Leading strip again.
sline = sline.lstrip()
words.extend(sline.split())
else:
sys.stdout.write(line)
|