def METHOD_NAME(module_paths: Iterable[Path]) -> Set[Tuple[Path, str]]:
    failed_rules: Set[Tuple[Path, str]] = set()
    # there are some rule dependencies that we need to run sequentially. eg proto and master
    max_workers = 1  # multiprocessing.cpu_count()
    with concurrent.futures.ThreadPoolExecutor(max_workers=max_workers) as executor:
        # collect the future to args mapping so we can print module path.
        future_to_rule = {
            executor.submit(run_rule, rule_path): rule_path for rule_path in module_paths
        }
        for future in concurrent.futures.as_completed(future_to_rule):
            rule_path = future_to_rule[future]
            try:
                return_code, msg = future.result()
                report_result(rule_path, return_code, msg)
                if return_code != 0:
                    failed_rules.add((rule_path, msg))
            except Exception as exc:
                print(f"{rule_path} generated an exception: {exc}", file=sys.stderr)
    return failed_rules