From 5e58e3f9cf3db5c3958fe6505eb59a2f814887fb Mon Sep 17 00:00:00 2001 From: Wayne Davison Date: Tue, 24 Jan 2006 19:02:55 +0000 Subject: [PATCH] The uid & gid are now stored using an id_pair structure. --- flist.c | 32 ++++++++++++-------------------- generator.c | 10 +++++----- rsync.c | 14 +++++++------- rsync.h | 8 ++++++-- uidlist.c | 35 ++++++++++++++++++++++++++++------- 5 files changed, 58 insertions(+), 41 deletions(-) diff --git a/flist.c b/flist.c index c6b1a721..277750c0 100644 --- a/flist.c +++ b/flist.c @@ -70,10 +70,10 @@ extern struct filter_list_struct server_filter_list; int io_error; int checksum_len; dev_t filesystem_dev; /* used to implement -x */ +unsigned int file_struct_len; static char empty_sum[MD4_SUM_LENGTH]; static int flist_count_offset; -static unsigned int file_struct_len; static void clean_flist(struct file_list *flist, int strip_root, int no_dups); static void output_flist(struct file_list *flist); @@ -362,14 +362,14 @@ static void send_file_entry(struct file_struct *file, int f) flags |= XMIT_RDEV_MINOR_IS_SMALL; } } - if (file->uid == uid) + if (file->ids->uid == uid) flags |= XMIT_SAME_UID; else - uid = file->uid; - if (file->gid == gid) + uid = file->ids->uid; + if (file->ids->gid == gid) flags |= XMIT_SAME_GID; else - gid = file->gid; + gid = file->ids->gid; if (file->modtime == modtime) flags |= XMIT_SAME_TIME; else @@ -619,12 +619,10 @@ static struct file_struct *receive_file_entry(struct file_list *flist, memset(bp, 0, file_struct_len); bp += file_struct_len; - file->flags = 0; file->modtime = modtime; file->length = file_length; file->mode = mode; - file->uid = uid; - file->gid = gid; + file->ids = id_pair(uid, gid); if (dirname_len) { file->dirname = lastdir = bp; @@ -880,8 +878,7 @@ struct file_struct *make_file(char *fname, struct file_list *flist, file->modtime = st.st_mtime; file->length = st.st_size; file->mode = st.st_mode; - file->uid = st.st_uid; - file->gid = st.st_gid; + file->ids = id_pair(st.st_uid, st.st_gid); #ifdef SUPPORT_HARD_LINKS if (flist && flist->hlink_pool) { @@ -948,8 +945,7 @@ struct file_struct *make_file(char *fname, struct file_list *flist, file->modtime = st2.st_mtime; file->length = st2.st_size; file->mode = st2.st_mode; - file->uid = st2.st_uid; - file->gid = st2.st_gid; + file->ids = id_pair(st2.st_uid, st2.st_gid); file->u.link = NULL; } else file->mode = save_mode; @@ -1324,8 +1320,6 @@ struct file_list *send_file_list(int f, int argc, char *argv[]) * without causing a compatibility problem with older versions. */ clean_flist(flist, 0, 0); - /* Now send the uid/gid list. This was introduced in - * protocol version 15 */ send_uid_list(f); /* send the io_error flag */ @@ -1395,9 +1389,7 @@ struct file_list *recv_file_list(int f) clean_flist(flist, relative_paths, 1); if (f >= 0) { - /* Now send the uid/gid list. This was introduced in - * protocol version 15 */ - recv_uid_list(f, flist); + recv_uid_list(f); /* Recv the io_error flag */ if (lp_ignore_errors(module_id) || ignore_errors) @@ -1624,11 +1616,11 @@ static void output_flist(struct file_list *flist) for (i = 0; i < flist->count; i++) { file = flist->files[i]; if ((am_root || am_sender) && preserve_uid) - sprintf(uidbuf, " uid=%ld", (long)file->uid); + sprintf(uidbuf, " uid=%ld", (long)file->ids->uid); else *uidbuf = '\0'; - if (preserve_gid && file->gid != GID_NONE) - sprintf(gidbuf, " gid=%ld", (long)file->gid); + if (preserve_gid && file->ids->gid != GID_NONE) + sprintf(gidbuf, " gid=%ld", (long)file->ids->gid); else *gidbuf = '\0'; if (!am_sender) diff --git a/generator.c b/generator.c index fb0bc2dd..0a63f00d 100644 --- a/generator.c +++ b/generator.c @@ -325,10 +325,10 @@ int unchanged_attrs(struct file_struct *file, STRUCT_STAT *st) && (st->st_mode & CHMOD_BITS) != (file->mode & CHMOD_BITS)) return 0; - if (am_root && preserve_uid && st->st_uid != file->uid) + if (am_root && preserve_uid && st->st_uid != file->ids->uid) return 0; - if (preserve_gid && file->gid != GID_NONE && st->st_gid != file->gid) + if (preserve_gid && file->ids->gid != GID_NONE && st->st_gid != file->ids->gid) return 0; return 1; @@ -351,10 +351,10 @@ void itemize(struct file_struct *file, int ndx, int statret, STRUCT_STAT *st, if (preserve_perms && (file->mode & CHMOD_BITS) != (st->st_mode & CHMOD_BITS)) iflags |= ITEM_REPORT_PERMS; - if (preserve_uid && am_root && file->uid != st->st_uid) + if (preserve_uid && am_root && file->ids->uid != st->st_uid) iflags |= ITEM_REPORT_OWNER; - if (preserve_gid && file->gid != GID_NONE - && st->st_gid != file->gid) + if (preserve_gid && file->ids->gid != GID_NONE + && st->st_gid != file->ids->gid) iflags |= ITEM_REPORT_GROUP; } else iflags |= ITEM_IS_NEW; diff --git a/rsync.c b/rsync.c index 9964c67e..d78a085e 100644 --- a/rsync.c +++ b/rsync.c @@ -82,9 +82,9 @@ int set_perms(char *fname,struct file_struct *file,STRUCT_STAT *st, updated = 1; } - change_uid = am_root && preserve_uid && st->st_uid != file->uid; - change_gid = preserve_gid && file->gid != GID_NONE - && st->st_gid != file->gid; + change_uid = am_root && preserve_uid && st->st_uid != file->ids->uid; + change_gid = preserve_gid && file->ids->gid != GID_NONE + && st->st_gid != file->ids->gid; #if !defined HAVE_LCHOWN && !defined CHOWN_MODIFIES_SYMLINK if (S_ISLNK(st->st_mode)) ; @@ -96,18 +96,18 @@ int set_perms(char *fname,struct file_struct *file,STRUCT_STAT *st, rprintf(FINFO, "set uid of %s from %ld to %ld\n", fname, - (long)st->st_uid, (long)file->uid); + (long)st->st_uid, (long)file->ids->uid); } if (change_gid) { rprintf(FINFO, "set gid of %s from %ld to %ld\n", fname, - (long)st->st_gid, (long)file->gid); + (long)st->st_gid, (long)file->ids->gid); } } if (do_lchown(fname, - change_uid ? file->uid : st->st_uid, - change_gid ? file->gid : st->st_gid) != 0) { + change_uid ? file->ids->uid : st->st_uid, + change_gid ? file->ids->gid : st->st_gid) != 0) { /* shouldn't have attempted to change uid or gid * unless have the privilege */ rsyserr(FERROR, errno, "%s %s failed", diff --git a/rsync.h b/rsync.h index 2a405320..dcc07998 100644 --- a/rsync.h +++ b/rsync.h @@ -493,6 +493,11 @@ struct hlink { int hlindex; }; +struct id_pair { + uid_t uid; + gid_t gid; +}; + #define F_DEV link_u.idev->dev #define F_INODE link_u.idev->inode @@ -516,9 +521,8 @@ struct file_struct { struct idev *idev; struct hlink *links; } link_u; + struct id_pair *ids; time_t modtime; - uid_t uid; - gid_t gid; mode_t mode; uchar flags; /* this item MUST remain last */ }; diff --git a/uidlist.c b/uidlist.c index b44b5d31..b9ab1b6c 100644 --- a/uidlist.c +++ b/uidlist.c @@ -46,6 +46,9 @@ struct idlist { static struct idlist *uidlist; static struct idlist *gidlist; +static struct id_pair *pair_list; +static int pair_cnt = 0, pair_alloc = 0; + static struct idlist *add_to_list(struct idlist **root, int id, char *name, int id2) { @@ -307,7 +310,7 @@ void send_uid_list(int f) /* recv a complete uid/gid mapping from the peer and map the uid/gid * in the file list to local names */ -void recv_uid_list(int f, struct file_list *flist) +void recv_uid_list(int f) { int id, i; char *name; @@ -336,14 +339,32 @@ void recv_uid_list(int f, struct file_list *flist) } } - /* now convert the uid/gid of all files in the list to the mapped - * uid/gid */ + /* Now convert the id_pair array over to mapped uid/gid values. */ if (am_root && preserve_uid && !numeric_ids) { - for (i = 0; i < flist->count; i++) - flist->files[i]->uid = match_uid(flist->files[i]->uid); + for (i = 0; i < pair_cnt; i++) + pair_list[i].uid = match_uid(pair_list[i].uid); } if (preserve_gid && (!am_root || !numeric_ids)) { - for (i = 0; i < flist->count; i++) - flist->files[i]->gid = match_gid(flist->files[i]->gid); + for (i = 0; i < pair_cnt; i++) + pair_list[i].gid = match_gid(pair_list[i].gid); + } +} + +struct id_pair *id_pair(uid_t uid, gid_t gid) +{ + int i; + + for (i = 0; i < pair_cnt; i++) { + if (uid == pair_list[i].uid && gid == pair_list[i].gid) + return pair_list + i; + } + + if (pair_cnt == pair_alloc) { + pair_alloc += 128; + pair_list = realloc_array(pair_list, struct id_pair, + pair_alloc); } + pair_list[pair_cnt].uid = uid; + pair_list[pair_cnt].gid = gid; + return pair_list + pair_cnt++; } -- 2.34.1