From 49982e22bf7044143c7bd72a596df8f5da9c334c Mon Sep 17 00:00:00 2001 From: Richard Berger Date: Sat, 13 Jun 2020 09:54:12 -0400 Subject: [PATCH] Add check for permissions --- cmake/Modules/CodingStandard.cmake | 10 +++ tools/coding_standard/permissions.py | 118 +++++++++++++++++++++++++++ tools/coding_standard/whitespace.py | 17 ++-- 3 files changed, 137 insertions(+), 8 deletions(-) create mode 100644 tools/coding_standard/permissions.py diff --git a/cmake/Modules/CodingStandard.cmake b/cmake/Modules/CodingStandard.cmake index 467dbb2b16..5a9c0e1dda 100644 --- a/cmake/Modules/CodingStandard.cmake +++ b/cmake/Modules/CodingStandard.cmake @@ -15,10 +15,20 @@ if (Python3_EXECUTABLE) ${Python3_EXECUTABLE} ${LAMMPS_TOOLS_DIR}/coding_standard/whitespace.py . WORKING_DIRECTORY ${LAMMPS_DIR} COMMENT "Check for whitespace errors") + add_custom_target( + check-permissions + ${Python3_EXECUTABLE} ${LAMMPS_TOOLS_DIR}/coding_standard/permissions.py . + WORKING_DIRECTORY ${LAMMPS_DIR} + COMMENT "Check for permission errors") add_custom_target( fix-whitespace ${Python3_EXECUTABLE} ${LAMMPS_TOOLS_DIR}/coding_standard/whitespace.py -f . WORKING_DIRECTORY ${LAMMPS_DIR} COMMENT "Fix whitespace errors") + add_custom_target( + fix-permissions + ${Python3_EXECUTABLE} ${LAMMPS_TOOLS_DIR}/coding_standard/permission.py -f . + WORKING_DIRECTORY ${LAMMPS_DIR} + COMMENT "Fix permission errors") endif() endif() diff --git a/tools/coding_standard/permissions.py b/tools/coding_standard/permissions.py new file mode 100644 index 0000000000..d956aed58c --- /dev/null +++ b/tools/coding_standard/permissions.py @@ -0,0 +1,118 @@ +#!/usr/bin/env python3 +# Utility for detecting and fixing file permission issues in LAMMPS +# +# Written by Richard Berger (Temple University) +import os +import glob +import yaml +import argparse +import stat + +DEFAULT_CONFIG = """ +permission: "rw-r--r--" +recursive: true +include: + - cmake/** + - doc/src/** + - python + - src/** + - examples/** + - tools/coding_standard +patterns: + - "*.c" + - "*.cmake" + - "*.cpp" + - "*.h" + - "*.jpg" + - "*.md" + - "*.pdf" + - "*.png" + - "*.rst" + - "*.tex" + - ".gitignore" + - "README" + - "in.*" + - "requirements.txt" +""" + +def check_permission(path, mask): + st = os.stat(path) + return bool(stat.S_IMODE(st.st_mode) == mask) + +def generate_permission_mask(line): + assert(len(line) == 9) + mask = 0 + + # USER + if line[0] == "r": + mask |= stat.S_IRUSR + if line[1] == "w": + mask |= stat.S_IWUSR + if line[2] == "x": + mask |= stat.S_IXUSR + + # GROUP + if line[3] == "r": + mask |= stat.S_IRGRP + if line[4] == "w": + mask |= stat.S_IWGRP + if line[5] == "x": + mask |= stat.S_IXGRP + + # OTHER + if line[6] == "r": + mask |= stat.S_IROTH + if line[7] == "w": + mask |= stat.S_IWOTH + if line[8] == "x": + mask |= stat.S_IXOTH + + return mask + +def check_folder(directory, config, fix=False, verbose=False): + files = [] + + for base_path in config['include']: + for pattern in config['patterns']: + path = os.path.join(directory, base_path, pattern) + files += glob.glob(path, recursive=config['recursive']) + + mask = generate_permission_mask(config['permission']) + + for f in files: + path = os.path.normpath(f) + + if verbose: + print("Checking file:", path) + + ok = check_permission(path, mask) + + if not ok: + print("[Error] Wrong file permissions @ {}".format(path)) + + if fix: + if os.access(path, os.W_OK): + print("Changing permissions of file {} to '{}'".format(path, config['permission'])) + os.chmod(path, mask) + else: + print("[Error] Can not write permissions of file {}".format(path)) + + +def main(): + parser = argparse.ArgumentParser(description='Utility for detecting and fixing file permission issues in LAMMPS') + parser.add_argument('-c', '--config', metavar='CONFIG_FILE', help='location of a optional configuration file') + parser.add_argument('-f', '--fix', action='store_true', help='automatically fix permissions') + parser.add_argument('-v', '--verbose', action='store_true', help='verbose output') + parser.add_argument('DIRECTORY', help='directory that should be checked') + args = parser.parse_args() + + if args.config: + with open(args.config, 'r') as cfile: + config = yaml.load(cfile, Loader=yaml.FullLoader) + else: + config = yaml.load(DEFAULT_CONFIG, Loader=yaml.FullLoader) + + check_folder(args.DIRECTORY, config, args.fix, args.verbose) + +if __name__ == "__main__": + main() diff --git a/tools/coding_standard/whitespace.py b/tools/coding_standard/whitespace.py index f9923893a0..04246ec704 100644 --- a/tools/coding_standard/whitespace.py +++ b/tools/coding_standard/whitespace.py @@ -17,18 +17,19 @@ include: - doc/src/** - python - src/** + - tools/coding_standard patterns: + - "*.c" + - "*.cmake" + - "*.cpp" + - "*.h" + - "*.md" + - "*.py" + - "*.rst" + - "*.sh" - ".gitignore" - "README" - "requirements.txt" - - "*.c" - - "*.cpp" - - "*.h" - - "*.sh" - - "*.py" - - "*.md" - - "*.rst" - - "*.cmake" """ def check_trailing_whitespace(f):