diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index da84ad3b02..d7c4be91e1 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -4,3 +4,20 @@ repos: hooks: - id: end-of-file-fixer exclude: '^(xls/contrib/.*|docs_src/bazel_rules_macros.md|.*\.(sh|ir|txt|patch|csv))$' + - repo: local + hooks: + - id: check-cpp-absolute-includes + name: Check C++ absolute includes + entry: xls/dev_tools/check_cpp_includes.py + language: python + files: ^xls/.*\.(h|cc)$ + exclude: ^xls/contrib/ + types: [text] + - repo: https://github.com/pylint-dev/pylint + rev: v3.3.4 + hooks: + - id: pylint + files: ^xls/dev_tools/check_.*.py$ + args: [ + --rcfile=.pylintrc + ] diff --git a/xls/dev_tools/check_cpp_includes.py b/xls/dev_tools/check_cpp_includes.py new file mode 100755 index 0000000000..0d45a7ddf3 --- /dev/null +++ b/xls/dev_tools/check_cpp_includes.py @@ -0,0 +1,75 @@ +#!/usr/bin/env python3 + +# Copyright 2025 The XLS Authors +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +"""Checks that C++ files only include absolute paths. + +This prevents accidental inclusion via relpath even if it happens to work. +""" + +import sys +import re + +ALLOWED_INCLUDE_STARTS = { + 'xls/', + 'absl/', + 'gmock/', + 'gtest/', + 'benchmark/', + 'llvm/', + 'fuzztest/', + 'verible/', + 're2/', + 'z3/', + 'google/protobuf/', + 'grpcpp/', + 'grpc/', + 'openssl/', + 'nlohmann/', + 'cppitertools/', + 'ortools/', + 'external/zstd/', + 'riegeli/', + 'tools/cpp/runfiles', + 'linenoise.h', + 'libs/json11/', + '%s', # For format strings embedded in files. +} + +def check_file(filename): + with open(filename, encoding='utf-8') as f: + content = f.read() + + # Look for quoted (non-system) includes + includes = re.findall(r'#include\s*"([^"]*)"', content) + bad_includes = [ + inc for inc in includes + if not any(inc.startswith(start) for start in ALLOWED_INCLUDE_STARTS)] + + if bad_includes: + print(f'{filename}: Found non-absolute includes:') + for include in bad_includes: + print(f' {include}') + return 1 + return 0 + +def main(): + exit_code = 0 + for filename in sys.argv[1:]: + exit_code |= check_file(filename) + sys.exit(exit_code) + +if __name__ == '__main__': + main() diff --git a/xls/dev_tools/check_examples_have_targets.py b/xls/dev_tools/check_examples_have_targets.py index 70beadf200..7a476770b8 100644 --- a/xls/dev_tools/check_examples_have_targets.py +++ b/xls/dev_tools/check_examples_have_targets.py @@ -96,7 +96,7 @@ def _to_target(relpath: str) -> str: def _does_file_seem_to_contain_tests(path: str) -> bool: - with open(path) as f: + with open(path, encoding='utf-8') as f: contents = f.read() return '#[test' in contents or '#[test_proc' in contents diff --git a/xls/dev_tools/check_header_guards.py b/xls/dev_tools/check_header_guards.py index 92b2cba0f8..e84a09caa4 100644 --- a/xls/dev_tools/check_header_guards.py +++ b/xls/dev_tools/check_header_guards.py @@ -32,7 +32,7 @@ def get_expected_guard(filepath, repo_root): def check_header_guard(filepath, expected_guard): - with open(filepath, 'r') as file: + with open(filepath, encoding='utf-8') as file: lines = file.readlines() # Check for the presence of the expected header guard. @@ -76,7 +76,8 @@ def main(): for file, expected, actual in non_compliant_files: print(file) print(f' want: {expected}') - print(f' got: {actual if actual else "None"}') + actual_str = actual if actual else 'None' + print(f' got: {actual_str}') sys.exit(-1) else: print('All header files are style compliant.') diff --git a/xls/jit/jit_channel_queue_benchmark.cc b/xls/jit/jit_channel_queue_benchmark.cc index 2ec26b266d..8c64669b52 100644 --- a/xls/jit/jit_channel_queue_benchmark.cc +++ b/xls/jit/jit_channel_queue_benchmark.cc @@ -19,7 +19,7 @@ #include #include "absl/log/check.h" -#include "include/benchmark/benchmark.h" +#include "benchmark/benchmark.h" #include "xls/ir/channel.h" #include "xls/ir/channel_ops.h" #include "xls/ir/package.h" diff --git a/xls/jit/value_to_native_layout_benchmark.cc b/xls/jit/value_to_native_layout_benchmark.cc index bd0272f467..df4916e496 100644 --- a/xls/jit/value_to_native_layout_benchmark.cc +++ b/xls/jit/value_to_native_layout_benchmark.cc @@ -17,7 +17,7 @@ #include #include -#include "include/benchmark/benchmark.h" +#include "benchmark/benchmark.h" #include "xls/interpreter/random_value.h" #include "xls/ir/ir_parser.h" #include "xls/ir/package.h"