[jit] Add contrib/jit-coverage-report.py

David Malcolm dmalcolm@redhat.com
Fri Jan 24 02:28:00 GMT 2014


Whilst reimplementing the API to remove the need to use callbacks, I
noticed that although all the tests were passing, some API functions
were still stubbed out in my new implementation i.e. we're missing test
coverage.

The following script (crudely) determines which API symbols are used
in which test cases, and prints a coverage report.

In particular the only remaining symbol with no coverage is
"gcc_jit_rvalue_access_field".

Committed to dmalcolm/jit branch:

contrib/
	* jit-coverage-report.py: New file: a script to print crude
	code-coverage information for the libgccjit API.
---
 contrib/ChangeLog.jit          |  4 +++
 contrib/jit-coverage-report.py | 67 ++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 71 insertions(+)
 create mode 100644 contrib/ChangeLog.jit
 create mode 100644 contrib/jit-coverage-report.py

diff --git a/contrib/ChangeLog.jit b/contrib/ChangeLog.jit
new file mode 100644
index 0000000..79be84d
--- /dev/null
+++ b/contrib/ChangeLog.jit
@@ -0,0 +1,4 @@
+2014-01-23  David Malcolm  <dmalcolm@redhat.com>
+
+	* jit-coverage-report.py: New file: a script to print crude
+	code-coverage information for the libgccjit API.
diff --git a/contrib/jit-coverage-report.py b/contrib/jit-coverage-report.py
new file mode 100644
index 0000000..529336f
--- /dev/null
+++ b/contrib/jit-coverage-report.py
@@ -0,0 +1,67 @@
+#! /usr/bin/python
+#
+# Print a report on which libgccjit.so symbols are used in which test
+# cases, and which lack test coverage.  Tested with Python 2.7 and 3.2
+# To be run from the root directory of the source tree.
+#
+# Copyright (C) 2014 Free Software Foundation, Inc.
+# Written by David Malcolm <dmalcolm@redhat.com>.
+#
+# This script is Free Software, and it can be copied, distributed and
+# modified as defined in the GNU General Public License.  A copy of
+# its license can be downloaded from http://www.gnu.org/copyleft/gpl.html
+
+from collections import Counter
+import glob
+import re
+import sys
+
+def parse_map_file(path):
+    """
+    Parse libgccjit.map, returning the symbols in the API as a list of str.
+    """
+    syms = []
+    with open(path) as f:
+        for line in f:
+            m = re.match('^\s+([a-z_]+);$', line)
+            if m:
+                syms.append(m.group(1))
+    return syms
+
+def parse_test_case(path):
+    """
+    Locate all symbol-like things in a C test case, yielding
+    them as a sequence of str.
+    """
+    with open(path) as f:
+        for line in f:
+            for m in re.finditer('([_A-Za-z][_A-Za-z0-9]*)', line):
+                yield m.group(1)
+
+def find_test_cases():
+    for path in glob.glob('gcc/testsuite/jit.dg/*.[ch]'):
+        yield path
+
+api_syms = parse_map_file('gcc/jit/libgccjit.map')
+
+syms_in_test_cases = {}
+for path in find_test_cases():
+    syms_in_test_cases[path] = list(parse_test_case(path))
+
+uses = Counter()
+for sym in sorted(api_syms):
+    print('symbol: %s' % sym)
+    uses[sym] = 0
+    for path in syms_in_test_cases:
+        count = syms_in_test_cases[path].count(sym)
+        uses[sym] += count
+        if count:
+            print('  uses in %s: %i' % (path, count))
+    if uses[sym] == 0:
+        print('  NEVER USED')
+    sys.stdout.write('\n')
+
+layout = '%40s  %5s  %s'
+print(layout % ('SYMBOL', 'USES', 'HISTOGRAM'))
+for sym, count in uses.most_common():
+    print(layout % (sym, count, '*' * count if count else 'UNUSED'))
-- 
1.7.11.7



More information about the Gcc-patches mailing list