diff options
author | Tavian Barnes <tavianator@tavianator.com> | 2017-06-15 20:14:22 -0400 |
---|---|---|
committer | Tavian Barnes <tavianator@tavianator.com> | 2017-06-15 20:14:22 -0400 |
commit | 05beda493cf176e8d689e9c5eaf4273a32be772f (patch) | |
tree | baa7b309a8ff03ec30e917362c9b9a44f29e6c90 /parse.c | |
parent | 45f5b5d2ecf2fea8ecf5817df22d1cbbab3518d1 (diff) |
-perm: Handle permcopy (e.g. u=rw,g=u) correctly
Diffstat (limited to 'parse.c')
-rw-r--r-- | parse.c | 21 |
1 files changed, 16 insertions, 5 deletions
@@ -1507,21 +1507,32 @@ static int parse_mode(const struct parser_state *state, const char *mode, struct break; case MODE_OP: - file_change = 0; - dir_change = 0; - switch (*i) { case 'u': + file_change = (expr->file_mode >> 6) & 07; + dir_change = (expr->dir_mode >> 6) & 07; + break; case 'g': + file_change = (expr->file_mode >> 3) & 07; + dir_change = (expr->dir_mode >> 3) & 07; + break; case 'o': - // PERMCOPY (e.g. u=g) has no effect for -perm - mstate = MODE_ACTION_APPLY; + file_change = expr->file_mode & 07; + dir_change = expr->dir_mode & 07; break; default: + file_change = 0; + dir_change = 0; mstate = MODE_PERM; continue; } + + file_change |= (file_change << 6) | (file_change << 3); + file_change &= who; + dir_change |= (dir_change << 6) | (dir_change << 3); + dir_change &= who; + mstate = MODE_ACTION_APPLY; break; case MODE_PERM: |