diff --git a/src/udev/udev-rules.c b/src/udev/udev-rules.c index fc1ef34964..e5a25bd119 100644 --- a/src/udev/udev-rules.c +++ b/src/udev/udev-rules.c @@ -1454,7 +1454,10 @@ int udev_rules_parse_file(UdevRules *rules, const char *filename, bool extra_che f = fopen(filename, "re"); if (!f) { - if (!extra_checks && errno == ENOENT) + if (extra_checks) + return -errno; + + if (errno == ENOENT) return 0; return log_warning_errno(errno, "Failed to open %s, ignoring: %m", filename); diff --git a/src/udev/udevadm-verify.c b/src/udev/udevadm-verify.c index 48aeb8f7e7..37c477da6a 100644 --- a/src/udev/udevadm-verify.c +++ b/src/udev/udevadm-verify.c @@ -12,6 +12,7 @@ #include "log.h" #include "parse-argument.h" #include "pretty-print.h" +#include "stat-util.h" #include "static-destruct.h" #include "strv.h" #include "udev-rules.h" @@ -119,20 +120,58 @@ static int verify_rules_file(UdevRules *rules, const char *fname) { return 0; } -static int verify_rules(UdevRules *rules, char **files) { - size_t fail_count = 0, success_count = 0; +static int verify_rules_filelist(UdevRules *rules, char **files, size_t *fail_count, size_t *success_count, bool walk_dirs); + +static int verify_rules_dir(UdevRules *rules, const char *dir, size_t *fail_count, size_t *success_count) { + int r; + _cleanup_strv_free_ char **files = NULL; + + assert(rules); + assert(dir); + assert(fail_count); + assert(success_count); + + r = conf_files_list(&files, ".rules", NULL, 0, dir); + if (r < 0) + return log_error_errno(r, "Failed to enumerate rules files: %m"); + + return verify_rules_filelist(rules, files, fail_count, success_count, /* walk_dirs */ false); +} + +static int verify_rules_filelist(UdevRules *rules, char **files, size_t *fail_count, size_t *success_count, bool walk_dirs) { int r, rv = 0; + assert(rules); + assert(files); + assert(fail_count); + assert(success_count); + STRV_FOREACH(fp, files) { - r = verify_rules_file(rules, *fp); - if (r < 0) { - fail_count++; - if (rv >= 0) - rv = r; - } else - success_count++; + if (walk_dirs && is_dir(*fp, /* follow = */ true) > 0) + r = verify_rules_dir(rules, *fp, fail_count, success_count); + else { + r = verify_rules_file(rules, *fp); + if (r < 0) + ++(*fail_count); + else + ++(*success_count); + } + if (r < 0 && rv >= 0) + rv = r; } + return rv; +} + +static int verify_rules(UdevRules *rules, char **files) { + size_t fail_count = 0, success_count = 0; + int r; + + assert(rules); + assert(files); + + r = verify_rules_filelist(rules, files, &fail_count, &success_count, /* walk_dirs */ true); + printf("\n%s%zu udev rules files have been checked.%s\n" " Success: %zu\n" "%s Fail: %zu%s\n", @@ -144,7 +183,7 @@ static int verify_rules(UdevRules *rules, char **files) { fail_count, fail_count > 0 ? ansi_normal() : ""); - return rv; + return r; } int verify_main(int argc, char *argv[], void *userdata) { diff --git a/test/units/testsuite-17.11.sh b/test/units/testsuite-17.11.sh index f1897b6785..d70a93b74f 100755 --- a/test/units/testsuite-17.11.sh +++ b/test/units/testsuite-17.11.sh @@ -31,6 +31,12 @@ cat >"${workdir}/default_output_1_fail" <"${workdir}/output_0_files" <"${out}" - if [ -f "${rules}" ]; then - diff -u "${workdir}/default_output_1_success" "${out}" + if [ -f "${exo}" ]; then + diff -u "${exo}" "${out}" + elif [ -f "${rules}" ]; then + diff -u "${workdir}/default_output_1_success" "${out}" fi next_test_number } assert_1() { + local rc set +e udevadm verify "$@" >"${out}" 2>"${err}" - assert_eq "$?" 1 + rc=$? set -e + assert_eq "$rc" 1 if [ -f "${exp}" ]; then diff -u "${exp}" "${err}" @@ -95,28 +105,40 @@ assert_1 -N now assert_1 --resolve-names # --resolve-names= takes "early" or "never" assert_1 --resolve-names=now -# Failed to parse rules file .: Is a directory -cp "${workdir}/default_output_1_fail" "${exo}" -assert_1 . # Failed to parse rules file ./nosuchfile: No such file or directory assert_1 ./nosuchfile -# Failed to parse rules file .: Is a directory +# Failed to parse rules file ./nosuchfile: No such file or directory cat >"${exo}" <"${workdir}/${exp}" cd - assert_1 --root="${workdir}" +cd - + +# udevadm verify path/ +sed "s|sample-[0-9]*.rules|${workdir}/${rules_dir}/&|" sample-*.exp >"${workdir}/${exp}" +cd - +assert_1 "${rules_dir}" +cd - exit 0