3 """Compiles a source file and checks errors against those listed in the file.
6 sys.argv[1]: a source file with contains the input and expected output
7 sys.argv[2]: the Flang frontend driver
8 sys.argv[3:]: Optional arguments to the Flang frontend driver"""
16 from difflib
import unified_diff
18 cm
.check_args(sys
.argv
)
19 srcdir
= cm
.set_source(sys
.argv
[1])
20 with
open(srcdir
, 'r') as f
:
27 flang_fc1
= cm
.set_executable(sys
.argv
[2])
28 flang_fc1_args
= sys
.argv
[3:]
29 flang_fc1_options
= "-fsyntax-only"
31 # Compiles, and reads in the output from the compilation process
32 cmd
= [flang_fc1
, *flang_fc1_args
, flang_fc1_options
, str(srcdir
)]
33 with tempfile
.TemporaryDirectory() as tmpdir
:
35 proc
= subprocess
.run(cmd
, stdout
=subprocess
.PIPE
, stderr
=subprocess
.PIPE
,
36 check
=True, universal_newlines
=True, cwd
=tmpdir
)
37 except subprocess
.CalledProcessError
as e
:
39 if e
.returncode
>= 128:
43 # Cleans up the output from the compilation process to be easier to process
44 for line
in log
.split('\n'):
45 m
= re
.search(r
"[^:]*:(\d+:).*(?:error|warning|portability|because):(.*)", line
)
47 if re
.search(r
"warning: .*fold.*host", line
):
48 continue # ignore host-dependent folding warnings
49 actual
+= m
.expand(r
"\1\2\n")
51 # Gets the expected errors and their line numbers
53 for i
, line
in enumerate(src
, 1):
54 m
= re
.search(r
"(?:^\s*!\s*(?:ERROR|WARNING|PORTABILITY|BECAUSE): )(.*)", line
)
56 errors
.append(m
.group(1))
60 expect
+= f
"{i}: {x}\n"
63 # Compares the expected errors with the compiler errors
64 for line
in unified_diff(actual
.split("\n"), expect
.split("\n"), n
=0):
65 line
= re
.sub(r
"(^\-)(\d+:)", r
"\nactual at \g<2>", line
)
66 line
= re
.sub(r
"(^\+)(\d+:)", r
"\nexpect at \g<2>", line
)