blob: 1bdbfed2cbc43793fb8506b57f8c35b48bcfedb9 [file] [log] [blame]
#!/usr/bin/env python3
# Copyright lowRISC contributors.
# Licensed under the Apache License, Version 2.0, see LICENSE for details.
# SPDX-License-Identifier: Apache-2.0
r"""Parses lint report and dump filtered messages in hjson format.
"""
import argparse
import logging as log
import re
import sys
from pathlib import Path
import hjson
def extract_messages(full_file, patterns, results):
"""
This extracts messages from the sting buffer full_file.
The argument patterns needs to be a list of tuples with
(<error_severity>, <pattern_to_match_for>).
"""
for severity, pattern in patterns:
results[severity] += re.findall(pattern, full_file, flags=re.MULTILINE)
return results
def get_results(resdir):
"""
Parse report and corresponding logfiles and extract error, warning
and info messages for each IP present in the result folder
"""
results = {
"tool": "ascentlint",
"errors": [],
"warnings": [],
"lint_errors": [],
"lint_warnings": [],
"lint_infos": []
}
try:
# check the log file for flow errors and warnings
with Path(resdir).joinpath('ascentlint.log').open() as f:
full_file = f.read()
err_warn_patterns = [("errors", r"^FlexNet Licensing error.*"),
("errors", r"^Error: .*"),
("errors", r"^ ERR .*"),
("warnings", r"^Warning: .*"),
("warnings", r"^ WARN .*")]
extract_messages(full_file, err_warn_patterns, results)
except IOError as err:
results["errors"] += ["IOError: %s" % err]
try:
# check the report file for lint INFO, WARNING and ERRORs
with Path(resdir).joinpath('ascentlint.rpt').open() as f:
full_file = f.read()
err_warn_patterns = {("lint_errors", r"^E .*"),
("lint_warnings", r"^W .*"),
("lint_infos", r"^I .*")}
extract_messages(full_file, err_warn_patterns, results)
except IOError as err:
results["errors"] += ["IOError: %s" % err]
return results
def main():
parser = argparse.ArgumentParser(
description="""This script parses AscentLint log and report files from
a lint run, filters the messages and creates an aggregated result
.hjson file with the following fields:
{"tool": "ascentlint",
"errors" : [],
"warnings" : [],
"lint_errors" : [],
"lint_warnings" : [],
"lint_infos" : []}
The fields 'errors' and 'warnings' contain file IO messages or
messages output by the tool itself, whereas the fields prefixed with
'lint_' contain lint-related messages.
The script returns nonzero status if any warnings or errors are present.
""")
parser.add_argument('--repdir',
type=str,
default="./",
help="""The script searches the 'ascentlint.log' and
'ascentlint.rpt' files in this directory.
Defaults to './'""")
parser.add_argument('--outdir',
type=str,
default="./",
help="""Output directory for the 'results.hjson' file.
Defaults to './'""")
args = parser.parse_args()
results = get_results(args.repdir)
with Path(args.outdir).joinpath("results.hjson").open("w") as results_file:
hjson.dump(results,
results_file,
ensure_ascii=False,
for_json=True,
use_decimal=True)
# return nonzero status if any warnings or errors are present
# lint infos do not count as failures
n_errors = len(results["errors"]) + len(results["lint_errors"])
n_warnings = len(results["warnings"]) + len(results["lint_warnings"])
if n_errors > 0 or n_warnings > 0:
log.info("Found %d lint errors and %d lint warnings", n_errors, n_warnings)
sys.exit(1)
log.info("Lint logfile parsed succesfully")
sys.exit(0)
if __name__ == "__main__":
main()