2014-03-22 02:11:47 +04:00
|
|
|
#!/usr/bin/env python
|
|
|
|
#convert line numbers in error messages according to "line directive" comments
|
2014-03-31 12:42:56 +04:00
|
|
|
import os
|
2014-03-22 02:11:47 +04:00
|
|
|
import sys
|
|
|
|
import re
|
|
|
|
import bisect
|
2014-03-31 12:42:56 +04:00
|
|
|
import subprocess
|
2014-03-22 02:11:47 +04:00
|
|
|
|
|
|
|
line_pattern = re.compile(
|
|
|
|
r'^// ###line ([0-9]+) "([^"]+)"\s*')
|
|
|
|
|
2014-03-31 12:42:56 +04:00
|
|
|
def _make_line_map(filename, stream=None):
|
2014-03-22 02:11:47 +04:00
|
|
|
"""
|
|
|
|
>>> from StringIO import StringIO
|
2014-03-31 12:42:56 +04:00
|
|
|
>>> _make_line_map('box',
|
|
|
|
... StringIO('''// ###line 3 "foo.bar"
|
2014-03-22 02:11:47 +04:00
|
|
|
... line 2
|
|
|
|
... line 3
|
|
|
|
... line 4
|
|
|
|
... // ###line 20 "baz.txt"
|
|
|
|
... line 6
|
|
|
|
... line 7
|
|
|
|
... '''))
|
2014-03-31 20:37:51 +04:00
|
|
|
[(0, 'box', 1), (1, 'foo.bar', 3), (5, 'baz.txt', 20)]
|
2014-03-22 02:11:47 +04:00
|
|
|
"""
|
2014-03-31 20:37:51 +04:00
|
|
|
result = [(0, filename, 1)]
|
2014-03-31 12:42:56 +04:00
|
|
|
input = stream or open(filename)
|
|
|
|
for i, l in enumerate(input.readlines()):
|
2014-03-22 02:11:47 +04:00
|
|
|
m = line_pattern.match(l)
|
|
|
|
if m:
|
|
|
|
result.append((i+1, m.group(2), int(m.group(1))))
|
|
|
|
return result
|
|
|
|
|
|
|
|
_line_maps = {}
|
|
|
|
|
|
|
|
def fline_map(filename):
|
|
|
|
map = _line_maps.get(filename)
|
|
|
|
if map is None:
|
2014-03-31 12:42:56 +04:00
|
|
|
map = _make_line_map(filename)
|
2014-03-22 02:11:47 +04:00
|
|
|
_line_maps[filename] = map
|
|
|
|
return map
|
|
|
|
|
|
|
|
def map_line(filename, line_num):
|
|
|
|
assert(line_num > 0)
|
|
|
|
map = fline_map(filename)
|
|
|
|
index = bisect.bisect_left(map, (line_num,'',0))
|
|
|
|
base = map[index - 1]
|
|
|
|
return base[1], base[2] + (line_num - base[0]-1)
|
|
|
|
|
|
|
|
def run():
|
2014-03-31 20:37:51 +04:00
|
|
|
if len(sys.argv) <= 1:
|
2014-03-22 02:11:47 +04:00
|
|
|
import doctest
|
|
|
|
doctest.testmod()
|
|
|
|
else:
|
2014-03-31 12:42:56 +04:00
|
|
|
dashes = sys.argv.index('--')
|
|
|
|
sources = sys.argv[1:dashes]
|
|
|
|
|
|
|
|
command = subprocess.Popen(
|
|
|
|
sys.argv[dashes + 1:], stderr = subprocess.STDOUT, stdout = subprocess.PIPE
|
|
|
|
)
|
|
|
|
|
|
|
|
error_pattern = re.compile(
|
|
|
|
'^(' + '|'.join(re.escape(s) for s in sources) + '):([0-9]+):([0-9]+):(.*)')
|
|
|
|
|
2014-03-22 02:11:47 +04:00
|
|
|
while True:
|
2014-03-31 12:42:56 +04:00
|
|
|
line = command.stdout.readline()
|
2014-03-22 02:11:47 +04:00
|
|
|
if line == '': break
|
|
|
|
m = error_pattern.match(line.rstrip('\n'))
|
|
|
|
if m:
|
|
|
|
file, line_num = map_line(m.group(1), int(m.group(2)))
|
2014-03-31 20:37:51 +04:00
|
|
|
line = '%s:%s:%s:%s\n' % (file, line_num, int(m.group(3)), m.group(4))
|
2014-03-22 02:11:47 +04:00
|
|
|
sys.stdout.write(line)
|
2014-03-31 12:42:56 +04:00
|
|
|
|
|
|
|
sys.exit(command.wait())
|
2014-03-22 02:11:47 +04:00
|
|
|
|
|
|
|
if __name__ == '__main__':
|
|
|
|
run()
|