Forráskód Böngészése

Merge branch 'practracker_regen'

Nick Mathewson 5 éve
szülő
commit
300e7d8c99

+ 3 - 0
Makefile.am

@@ -352,6 +352,9 @@ if USEPYTHON
 	$(PYTHON) $(top_srcdir)/scripts/maint/practracker/practracker.py $(top_srcdir)
 	$(PYTHON) $(top_srcdir)/scripts/maint/practracker/practracker.py $(top_srcdir)
 endif
 endif
 
 
+practracker-regen:
+	$(PYTHON) $(top_srcdir)/scripts/maint/practracker/practracker.py --regen $(top_srcdir)
+
 check-docs: all
 check-docs: all
 	$(PERL) $(top_builddir)/scripts/maint/checkOptionDocs.pl
 	$(PERL) $(top_builddir)/scripts/maint/checkOptionDocs.pl
 
 

+ 70 - 12
scripts/maint/practracker/practracker.py

@@ -13,9 +13,9 @@ practracker.py should be run with its second argument pointing to the Tor
 top-level source directory like this:
 top-level source directory like this:
   $ python3 ./scripts/maint/practracker/practracker.py .
   $ python3 ./scripts/maint/practracker/practracker.py .
 
 
-The exceptions file is meant to be initialized once with the current state of
-the source code and then get saved in the repository for ever after:
-  $ python3 ./scripts/maint/practracker/practracker.py . > ./scripts/maint/practracker/exceptions.txt
+To regenerate the exceptions file so that it allows all current
+problems in the Tor source, use the --regen flag:
+  $ python3 --regen ./scripts/maint/practracker/practracker.py .
 """
 """
 
 
 from __future__ import print_function
 from __future__ import print_function
@@ -120,14 +120,59 @@ def consider_metrics_for_file(fname, f):
 
 
     return found_new_issues
     return found_new_issues
 
 
-def main():
-    if (len(sys.argv) != 2):
-        print("Usage:\n\t$ practracker.py <tor topdir>\n\t(e.g. $ practracker.py ~/tor/)")
-        return
+HEADER="""\
+# Welcome to the exceptions file for Tor's best-practices tracker!
+#
+# Each line of this file represents a single violation of Tor's best
+# practices -- typically, a violation that we had before practracker.py
+# first existed.
+#
+# There are three kinds of problems that we recognize right now:
+#   function-size -- a function of more than {MAX_FUNCTION_SIZE} lines.
+#   file-size -- a file of more than {MAX_FILE_SIZE} lines.
+#   include-count -- a file with more than {MAX_INCLUDE_COUNT} #includes.
+#
+# Each line below represents a single exception that practracker should
+# _ignore_. Each line has four parts:
+#  1. The word "problem".
+#  2. The kind of problem.
+#  3. The location of the problem: either a filename, or a
+#     filename:functionname pair.
+#  4. The magnitude of the problem to ignore.
+#
+# So for example, consider this line:
+#    problem file-size /src/core/or/connection_or.c 3200
+#
+# It tells practracker to allow the mentioned file to be up to 3200 lines
+# long, even though ordinarily it would warn about any file with more than
+# {MAX_FILE_SIZE} lines.
+#
+# You can either edit this file by hand, or regenerate it completely by
+# running `make practracker-regen`.
+#
+# Remember: It is better to fix the problem than to add a new exception!
+
+""".format(**globals())
+
+def main(argv):
+    import argparse
+
+    progname = argv[0]
+    parser = argparse.ArgumentParser(prog=progname)
+    parser.add_argument("--regen", action="store_true",
+                        help="Regenerate the exceptions file")
+    parser.add_argument("--exceptions",
+                        help="Override the location for the exceptions file")
+    parser.add_argument("topdir", default=".", nargs="?",
+                        help="Top-level directory for the tor source")
+    args = parser.parse_args(argv[1:])
 
 
     global TOR_TOPDIR
     global TOR_TOPDIR
-    TOR_TOPDIR = sys.argv[1]
-    exceptions_file = os.path.join(TOR_TOPDIR, "scripts/maint/practracker", EXCEPTIONS_FNAME)
+    TOR_TOPDIR = args.topdir
+    if args.exceptions:
+        exceptions_file = args.exceptions
+    else:
+        exceptions_file = os.path.join(TOR_TOPDIR, "scripts/maint/practracker", EXCEPTIONS_FNAME)
 
 
     # 1) Get all the .c files we care about
     # 1) Get all the .c files we care about
     files_list = util.get_tor_c_files(TOR_TOPDIR)
     files_list = util.get_tor_c_files(TOR_TOPDIR)
@@ -135,13 +180,26 @@ def main():
     # 2) Initialize problem vault and load an optional exceptions file so that
     # 2) Initialize problem vault and load an optional exceptions file so that
     # we don't warn about the past
     # we don't warn about the past
     global ProblemVault
     global ProblemVault
-    ProblemVault = problem.ProblemVault(exceptions_file)
+
+    if args.regen:
+        tmpname = exceptions_file + ".tmp"
+        tmpfile = open(tmpname, "w")
+        sys.stdout = tmpfile
+        sys.stdout.write(HEADER)
+        ProblemVault = problem.ProblemVault()
+    else:
+        ProblemVault = problem.ProblemVault(exceptions_file)
 
 
     # 3) Go through all the files and report problems if they are not exceptions
     # 3) Go through all the files and report problems if they are not exceptions
     found_new_issues = consider_all_metrics(files_list)
     found_new_issues = consider_all_metrics(files_list)
 
 
+    if args.regen:
+        tmpfile.close()
+        os.rename(tmpname, exceptions_file)
+        sys.exit(0)
+
     # If new issues were found, try to give out some advice to the developer on how to resolve it.
     # If new issues were found, try to give out some advice to the developer on how to resolve it.
-    if (found_new_issues):
+    if found_new_issues and not args.regen:
         new_issues_str = """\
         new_issues_str = """\
 FAILURE: practracker found new problems in the code: see warnings above.
 FAILURE: practracker found new problems in the code: see warnings above.
 
 
@@ -155,4 +213,4 @@ See doc/HACKING/HelpfulTools.md for more information on using practracker.\
     sys.exit(found_new_issues)
     sys.exit(found_new_issues)
 
 
 if __name__ == '__main__':
 if __name__ == '__main__':
-    main()
+    main(sys.argv)

+ 4 - 1
scripts/maint/practracker/problem.py

@@ -19,10 +19,13 @@ class ProblemVault(object):
     found in the code, and also the old problems we read from the exception
     found in the code, and also the old problems we read from the exception
     file.
     file.
     """
     """
-    def __init__(self, exception_fname):
+    def __init__(self, exception_fname=None):
         # Exception dictionary: { problem.key() : Problem object }
         # Exception dictionary: { problem.key() : Problem object }
         self.exceptions = {}
         self.exceptions = {}
 
 
+        if exception_fname == None:
+            return
+
         try:
         try:
             with open(exception_fname, 'r') as exception_f:
             with open(exception_fname, 'r') as exception_f:
                 self.register_exceptions(exception_f)
                 self.register_exceptions(exception_f)