From aeff24ee344e5b9c4f2f9040a02320952e70ccd7 Mon Sep 17 00:00:00 2001 From: Tavian Barnes Date: Wed, 10 Feb 2016 22:15:41 -0500 Subject: Implement -samefile. --- parse.c | 48 +++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 41 insertions(+), 7 deletions(-) (limited to 'parse.c') diff --git a/parse.c b/parse.c index 4613aed..3498901 100644 --- a/parse.c +++ b/parse.c @@ -148,6 +148,21 @@ struct parser_state { struct timespec now; }; +/** + * Invoke stat() on an argument. + */ +static int stat_arg(const struct parser_state *state, struct expr *expr, struct stat *sb) { + bool follow = state->cl->flags & BFTW_FOLLOW; + int flags = follow ? 0 : AT_SYMLINK_NOFOLLOW; + + int ret = fstatat(AT_FDCWD, expr->sdata, sb, flags); + if (ret != 0) { + print_error(NULL, expr->sdata, errno); + free_expr(expr); + } + return ret; +} + /** * Parse the expression specified on the command line. */ @@ -344,13 +359,7 @@ static struct expr *parse_acnewer(struct parser_state *state, const char *option } struct stat sb; - - bool follow = state->cl->flags & BFTW_FOLLOW; - int flags = follow ? 0 : AT_SYMLINK_NOFOLLOW; - - if (fstatat(AT_FDCWD, expr->sdata, &sb, flags) != 0) { - print_error(NULL, expr->sdata, errno); - free_expr(expr); + if (stat_arg(state, expr, &sb) != 0) { return NULL; } @@ -408,6 +417,26 @@ static struct expr *parse_depth(struct parser_state *state, const char *option, return new_option(state, option); } +/** + * Parse -samefile FILE. + */ +static struct expr *parse_samefile(struct parser_state *state, const char *option) { + struct expr *expr = parse_test_sdata(state, option, eval_samefile); + if (!expr) { + return NULL; + } + + struct stat sb; + if (stat_arg(state, expr, &sb) != 0) { + return NULL; + } + + expr->dev = sb.st_dev; + expr->ino = sb.st_ino; + + return expr; +} + /** * Parse -type [bcdpfls]. */ @@ -619,6 +648,11 @@ static struct expr *parse_literal(struct parser_state *state) { } break; + case 's': + if (strcmp(arg, "-samefile") == 0) { + return parse_samefile(state, arg); + } + case 't': if (strcmp(arg, "-true") == 0) { return &expr_true; -- cgit v1.2.3