From 8901d15087b224610a26c829635d5d305b02307b Mon Sep 17 00:00:00 2001 From: nathan Date: Thu, 30 Jul 2009 19:29:04 +0000 Subject: [PATCH] b=20030 i=thomas.leibovici@cea.fr i=adilger return changelog entries as a struct from llapi --- lustre/include/lustre/liblustreapi.h | 21 ++++-- lustre/include/lustre/lustre_idl.h | 55 ++------------- lustre/include/lustre/lustre_user.h | 56 ++++++++++++++- lustre/mdd/mdd_device.c | 26 +++---- lustre/mdd/mdd_dir.c | 12 ++-- lustre/mdd/mdd_lproc.c | 13 +--- lustre/mdd/mdd_object.c | 8 +-- lustre/mds/mds_log.c | 2 +- lustre/obdclass/llog_swab.c | 16 ++--- lustre/obdclass/lprocfs_status.c | 47 +++++++------ lustre/ptlrpc/wiretest.c | 72 +++++++++++--------- lustre/utils/lfs.c | 106 ++++++++--------------------- lustre/utils/liblustreapi.c | 128 ++++++++++++++++++++++++++++++++--- lustre/utils/lreplicate.c | 128 ++++++++++++----------------------- lustre/utils/wirecheck.c | 25 ++++--- lustre/utils/wiretest.c | 72 +++++++++++--------- 16 files changed, 424 insertions(+), 363 deletions(-) diff --git a/lustre/include/lustre/liblustreapi.h b/lustre/include/lustre/liblustreapi.h index cde0b68..59fc25d 100644 --- a/lustre/include/lustre/liblustreapi.h +++ b/lustre/include/lustre/liblustreapi.h @@ -182,14 +182,23 @@ extern int llapi_rsetfacl(int argc, char *argv[]); extern int llapi_rgetfacl(int argc, char *argv[]); extern int llapi_cp(int argc, char *argv[]); extern int llapi_ls(int argc, char *argv[]); -extern int llapi_changelog_open(const char *mdtname, long long startrec); -extern int llapi_changelog_clear(const char *mdtname, const char *idstr, - long long endrec); -extern int llapi_changelog_register(const char *mdtname); -extern int llapi_changelog_unregister(const char *mdtname, int id); extern int llapi_fid2path(const char *device, const char *fidstr, char *path, int pathlen, long long *recno, int *linkno); -/* HSM copytool interface. priv is private copytool state, managed internally +extern int llapi_path2fid(const char *path, lustre_fid *fid); + +/* Changelog interface. priv is private state, managed internally + by these functions */ +#define CHANGELOG_FLAG_FOLLOW 0x01 +extern int llapi_changelog_start(void **priv, int flags, const char *mdtname, + long long startrec); +extern int llapi_changelog_fini(void **priv); +extern int llapi_changelog_recv(void *priv, struct changelog_rec **rech); +extern int llapi_changelog_free(struct changelog_rec **rech); +/* Allow records up to endrec to be destroyed; requires registered id. */ +extern int llapi_changelog_clear(const char *mdtname, const char *idstr, + long long endrec); + +/* HSM copytool interface. priv is private state, managed internally by these functions */ extern int llapi_copytool_start(void **priv, int flags, int archive_num_count, int *archive_nums); diff --git a/lustre/include/lustre/lustre_idl.h b/lustre/include/lustre/lustre_idl.h index e2e43c2..e29996f 100644 --- a/lustre/include/lustre/lustre_idl.h +++ b/lustre/include/lustre/lustre_idl.h @@ -2319,48 +2319,14 @@ struct llog_size_change_rec { } __attribute__((packed)); #define CHANGELOG_MAGIC 0xca103000 -/** Changelog record types - * When adding record types, update mdd_lproc.c's changelog_str - */ -enum changelog_rec_type { - CL_MARK = 0, - CL_CREATE = 1, /* namespace */ - CL_MKDIR = 2, /* namespace */ - CL_HARDLINK = 3, /* namespace */ - CL_SOFTLINK = 4, /* namespace */ - CL_MKNOD = 5, /* namespace */ - CL_UNLINK = 6, /* namespace */ - CL_RMDIR = 7, /* namespace */ - CL_RENAME = 8, /* namespace */ - CL_EXT = 9, /* namespace extended record (2nd half of rename) */ - CL_OPEN = 10, /* not currently used */ - CL_CLOSE = 11, /* may be written to log only with mtime change */ - CL_IOCTL = 12, - CL_TRUNC = 13, - CL_SETATTR = 14, - CL_XATTR = 15, - CL_LAST -}; - -/** Changelog entry type names. Must be defined in the same order as the - * \a changelog_rec_type enum. - */ -#define DECLARE_CHANGELOG_NAMES static const char *changelog_str[] = \ - {"MARK","CREAT","MKDIR","HLINK","SLINK","MKNOD","UNLNK","RMDIR", \ - "RNMFM","RNMTO","OPEN","CLOSE","IOCTL","TRUNC","SATTR","XATTR"} /** \a changelog_rec_type's that can't be masked */ #define CHANGELOG_MINMASK (1 << CL_MARK) /** bits covering all \a changelog_rec_type's */ -#define CHANGELOG_ALLMASK 0XFFFF +#define CHANGELOG_ALLMASK 0XFFFFFFFF /** default \a changelog_rec_type mask */ #define CHANGELOG_DEFMASK CHANGELOG_ALLMASK -/* per-record flags */ -#define CLF_VERSION 0x1000 -#define CLF_FLAGMASK 0x0FFF -#define CLF_HSM 0x0001 - /* changelog llog name, needed by client replicators */ #define CHANGELOG_CATALOG "changelog_catalog" @@ -2371,22 +2337,9 @@ struct changelog_setinfo { /** changelog record */ struct llog_changelog_rec { - struct llog_rec_hdr cr_hdr; - __u16 cr_flags; /**< (flags&CLF_FLAGMASK)|CLF_VERSION */ - __u16 cr_namelen; - __u32 cr_type; /**< \a changelog_rec_type */ - __u64 cr_index; - __u64 cr_prev; /**< last index for this target fid */ - __u64 cr_time; - union { - struct lu_fid cr_tfid; /**< target fid */ - __u32 cr_markerflags; /**< CL_MARK flags */ - }; - struct lu_fid cr_pfid; /**< parent fid */ - union { - char cr_name[0]; /**< last element */ - struct llog_rec_tail cr_tail; /**< for_sizezof_only */ - }; + struct llog_rec_hdr cr_hdr; + struct changelog_rec cr; + struct llog_rec_tail cr_tail; /**< for_sizezof_only */ } __attribute__((packed)); #define CHANGELOG_USER_PREFIX "cl" diff --git a/lustre/include/lustre/lustre_user.h b/lustre/include/lustre/lustre_user.h index 87643f8..eb58cd8 100644 --- a/lustre/include/lustre/lustre_user.h +++ b/lustre/include/lustre/lustre_user.h @@ -417,7 +417,58 @@ struct if_quotactl { }; -/********* Misc **********/ +/********* Changelogs **********/ +/** Changelog record types */ +enum changelog_rec_type { + CL_MARK = 0, + CL_CREATE = 1, /* namespace */ + CL_MKDIR = 2, /* namespace */ + CL_HARDLINK = 3, /* namespace */ + CL_SOFTLINK = 4, /* namespace */ + CL_MKNOD = 5, /* namespace */ + CL_UNLINK = 6, /* namespace */ + CL_RMDIR = 7, /* namespace */ + CL_RENAME = 8, /* namespace */ + CL_EXT = 9, /* namespace extended record (2nd half of rename) */ + CL_OPEN = 10, /* not currently used */ + CL_CLOSE = 11, /* may be written to log only with mtime change */ + CL_IOCTL = 12, + CL_TRUNC = 13, + CL_SETATTR = 14, + CL_XATTR = 15, + CL_HSM = 16, /* HSM specific events, see flags */ + CL_LAST +}; + +static inline const char *changelog_type2str(int type) { + static const char *changelog_str[] = { + "MARK", "CREAT", "MKDIR", "HLINK", "SLINK", "MKNOD", "UNLNK", + "RMDIR", "RNMFM", "RNMTO", "OPEN", "CLOSE", "IOCTL", "TRUNC", + "SATTR", "XATTR", "HSM" }; + if (type >= 0 && type < CL_LAST) + return changelog_str[type]; + return NULL; +} + +/* per-record flags */ +#define CLF_VERSION 0x1000 +#define CLF_FLAGMASK 0x0FFF +/* Anything under the flagmask may be per-type (if desired) */ + +struct changelog_rec { + __u16 cr_namelen; + __u16 cr_flags; /**< (flags&CLF_FLAGMASK)|CLF_VERSION */ + __u32 cr_type; /**< \a changelog_rec_type */ + __u64 cr_index; /**< changelog record number */ + __u64 cr_prev; /**< last index for this target fid */ + __u64 cr_time; + union { + lustre_fid cr_tfid; /**< target fid */ + __u32 cr_markerflags; /**< CL_MARK flags */ + }; + lustre_fid cr_pfid; /**< parent fid */ + char cr_name[0]; /**< last element */ +} __attribute__((packed)); struct ioc_changelog_clear { __u32 icc_mdtindex; @@ -425,6 +476,9 @@ struct ioc_changelog_clear { __u64 icc_recno; }; + +/********* Misc **********/ + #ifndef offsetof # define offsetof(typ,memb) ((unsigned long)((char *)&(((typ *)0)->memb))) #endif diff --git a/lustre/mdd/mdd_device.c b/lustre/mdd/mdd_device.c index 302b1d5..16fefbd 100644 --- a/lustre/mdd/mdd_device.c +++ b/lustre/mdd/mdd_device.c @@ -148,11 +148,11 @@ static int changelog_init_cb(struct llog_handle *llh, struct llog_rec_hdr *hdr, CDEBUG(D_INFO, "seeing record at index %d/%d/"LPU64" t=%x %.*s in log "LPX64"\n", - hdr->lrh_index, rec->cr_hdr.lrh_index, rec->cr_index, - rec->cr_type, rec->cr_namelen, rec->cr_name, + hdr->lrh_index, rec->cr_hdr.lrh_index, rec->cr.cr_index, + rec->cr.cr_type, rec->cr.cr_namelen, rec->cr.cr_name, llh->lgh_id.lgl_oid); - mdd->mdd_cl.mc_index = rec->cr_index; + mdd->mdd_cl.mc_index = rec->cr.cr_index; RETURN(LLOG_PROC_BREAK); } @@ -303,18 +303,18 @@ int mdd_changelog_llog_write(struct mdd_device *mdd, struct llog_ctxt *ctxt; int rc; - if ((mdd->mdd_cl.mc_mask & (1 << rec->cr_type)) == 0) + if ((mdd->mdd_cl.mc_mask & (1 << rec->cr.cr_type)) == 0) return 0; - rec->cr_hdr.lrh_len = llog_data_len(sizeof(*rec) + rec->cr_namelen); + rec->cr_hdr.lrh_len = llog_data_len(sizeof(*rec) + rec->cr.cr_namelen); /* llog_lvfs_write_rec sets the llog tail len */ rec->cr_hdr.lrh_type = CHANGELOG_REC; - rec->cr_time = cfs_time_current_64(); + rec->cr.cr_time = cfs_time_current_64(); spin_lock(&mdd->mdd_cl.mc_lock); /* NB: I suppose it's possible llog_add adds out of order wrt cr_index, but as long as the MDD transactions are ordered correctly for e.g. rename conflicts, I don't think this should matter. */ - rec->cr_index = ++mdd->mdd_cl.mc_index; + rec->cr.cr_index = ++mdd->mdd_cl.mc_index; spin_unlock(&mdd->mdd_cl.mc_lock); ctxt = llog_get_context(obd, LLOG_CHANGELOG_ORIG_CTXT); if (ctxt == NULL) @@ -396,17 +396,17 @@ int mdd_changelog_write_header(struct mdd_device *mdd, int markerflags) if (rec == NULL) RETURN(-ENOMEM); - rec->cr_flags = CLF_VERSION; - rec->cr_type = CL_MARK; - rec->cr_namelen = len; - memcpy(rec->cr_name, obd->obd_name, rec->cr_namelen); + rec->cr.cr_flags = CLF_VERSION; + rec->cr.cr_type = CL_MARK; + rec->cr.cr_namelen = len; + memcpy(rec->cr.cr_name, obd->obd_name, rec->cr.cr_namelen); /* Status and action flags */ - rec->cr_markerflags = mdd->mdd_cl.mc_flags | markerflags; + rec->cr.cr_markerflags = mdd->mdd_cl.mc_flags | markerflags; rc = mdd_changelog_llog_write(mdd, rec, NULL); /* assume on or off event; reset repeat-access time */ - mdd->mdd_cl.mc_starttime = rec->cr_time; + mdd->mdd_cl.mc_starttime = rec->cr.cr_time; OBD_FREE(rec, reclen); RETURN(rc); diff --git a/lustre/mdd/mdd_dir.c b/lustre/mdd/mdd_dir.c index d1cf1f4..06561d9 100644 --- a/lustre/mdd/mdd_dir.c +++ b/lustre/mdd/mdd_dir.c @@ -647,13 +647,13 @@ static int mdd_changelog_ns_store(const struct lu_env *env, RETURN(-ENOMEM); rec = (struct llog_changelog_rec *)buf->lb_buf; - rec->cr_flags = CLF_VERSION; - rec->cr_type = (__u32)type; + rec->cr.cr_flags = CLF_VERSION; + rec->cr.cr_type = (__u32)type; tfid = tf ? tf : mdo2fid(target); - rec->cr_tfid = *tfid; - rec->cr_pfid = *tpfid; - rec->cr_namelen = tname->ln_namelen; - memcpy(rec->cr_name, tname->ln_name, rec->cr_namelen); + rec->cr.cr_tfid = *tfid; + rec->cr.cr_pfid = *tpfid; + rec->cr.cr_namelen = tname->ln_namelen; + memcpy(rec->cr.cr_name, tname->ln_name, rec->cr.cr_namelen); if (likely(target)) target->mod_cltime = cfs_time_current_64(); diff --git a/lustre/mdd/mdd_lproc.c b/lustre/mdd/mdd_lproc.c index 903a675..3784927 100644 --- a/lustre/mdd/mdd_lproc.c +++ b/lustre/mdd/mdd_lproc.c @@ -155,15 +155,6 @@ static int lprocfs_rd_atime_diff(char *page, char **start, off_t off, /**** changelogs ****/ -DECLARE_CHANGELOG_NAMES; - -const char *changelog_bit2str(int bit) -{ - if (bit < CL_LAST) - return changelog_str[bit]; - return NULL; -} - static int lprocfs_rd_changelog_mask(char *page, char **start, off_t off, int count, int *eof, void *data) { @@ -174,7 +165,7 @@ static int lprocfs_rd_changelog_mask(char *page, char **start, off_t off, while (i < CL_LAST) { if (mdd->mdd_cl.mc_mask & (1 << i)) rc += snprintf(page + rc, count - rc, "%s ", - changelog_str[i]); + changelog_type2str(i)); i++; } return rc; @@ -197,7 +188,7 @@ static int lprocfs_wr_changelog_mask(struct file *file, const char *buffer, GOTO(out, rc = -EFAULT); kernbuf[count] = 0; - rc = libcfs_str2mask(kernbuf, changelog_bit2str, &mdd->mdd_cl.mc_mask, + rc = libcfs_str2mask(kernbuf, changelog_type2str, &mdd->mdd_cl.mc_mask, CHANGELOG_MINMASK, CHANGELOG_ALLMASK); if (rc == 0) rc = count; diff --git a/lustre/mdd/mdd_object.c b/lustre/mdd/mdd_object.c index e04f1c8..070847e 100644 --- a/lustre/mdd/mdd_object.c +++ b/lustre/mdd/mdd_object.c @@ -1200,10 +1200,10 @@ static int mdd_changelog_data_store(const struct lu_env *env, RETURN(-ENOMEM); rec = (struct llog_changelog_rec *)buf->lb_buf; - rec->cr_flags = CLF_VERSION; - rec->cr_type = (__u32)type; - rec->cr_tfid = *tfid; - rec->cr_namelen = 0; + rec->cr.cr_flags = CLF_VERSION; + rec->cr.cr_type = (__u32)type; + rec->cr.cr_tfid = *tfid; + rec->cr.cr_namelen = 0; mdd_obj->mod_cltime = cfs_time_current_64(); rc = mdd_changelog_llog_write(mdd, rec, handle); diff --git a/lustre/mds/mds_log.c b/lustre/mds/mds_log.c index 17393d2..0108623 100644 --- a/lustre/mds/mds_log.c +++ b/lustre/mds/mds_log.c @@ -127,7 +127,7 @@ static int llog_changelog_cancel_cb(struct llog_handle *llh, /* This is always a (sub)log, not the catalog */ LASSERT(llh->lgh_hdr->llh_flags & LLOG_F_IS_PLAIN); - if (rec->cr_index > endrec) + if (rec->cr.cr_index > endrec) /* records are in order, so we're done */ RETURN(LLOG_PROC_BREAK); diff --git a/lustre/obdclass/llog_swab.c b/lustre/obdclass/llog_swab.c index 1602044..8c49fc7 100644 --- a/lustre/obdclass/llog_swab.c +++ b/lustre/obdclass/llog_swab.c @@ -156,14 +156,14 @@ void lustre_swab_llog_rec(struct llog_rec_hdr *rec, struct llog_rec_tail *tail) case CHANGELOG_REC: { struct llog_changelog_rec *cr = (struct llog_changelog_rec*)rec; - __swab16s(&cr->cr_flags); - __swab16s(&cr->cr_namelen); - __swab32s(&cr->cr_type); - __swab64s(&cr->cr_index); - __swab64s(&cr->cr_prev); - __swab64s(&cr->cr_time); - lustre_swab_lu_fid(&cr->cr_tfid); - lustre_swab_lu_fid(&cr->cr_pfid); + __swab16s(&cr->cr.cr_namelen); + __swab16s(&cr->cr.cr_flags); + __swab32s(&cr->cr.cr_type); + __swab64s(&cr->cr.cr_index); + __swab64s(&cr->cr.cr_prev); + __swab64s(&cr->cr.cr_time); + lustre_swab_lu_fid(&cr->cr.cr_tfid); + lustre_swab_lu_fid(&cr->cr.cr_pfid); break; } diff --git a/lustre/obdclass/lprocfs_status.c b/lustre/obdclass/lprocfs_status.c index 6c5e052..b1224aa 100644 --- a/lustre/obdclass/lprocfs_status.c +++ b/lustre/obdclass/lprocfs_status.c @@ -2233,8 +2233,6 @@ EXPORT_SYMBOL(lprocfs_obd_wr_recovery_maxtime); /**** Changelogs *****/ #define D_CHANGELOG 0 -DECLARE_CHANGELOG_NAMES; - /* How many records per seq_show. Too small, we spawn llog_process threads too often; too large, we run out of buffer space */ #define CHANGELOG_CHUNK_SIZE 100 @@ -2245,25 +2243,26 @@ static int changelog_show_cb(struct llog_handle *llh, struct llog_rec_hdr *hdr, struct seq_file *seq = (struct seq_file *)data; struct changelog_seq_iter *csi = seq->private; struct llog_changelog_rec *rec = (struct llog_changelog_rec *)hdr; - int rc; + char *ptr; + int cnt, rc; ENTRY; if ((rec->cr_hdr.lrh_type != CHANGELOG_REC) || - (rec->cr_type >= CL_LAST)) { + (rec->cr.cr_type >= CL_LAST)) { CERROR("Not a changelog rec %d/%d\n", rec->cr_hdr.lrh_type, - rec->cr_type); + rec->cr.cr_type); RETURN(-EINVAL); } CDEBUG(D_CHANGELOG, "rec="LPU64" start="LPU64" cat=%d:%d start=%d:%d\n", - rec->cr_index, csi->csi_startrec, + rec->cr.cr_index, csi->csi_startrec, llh->lgh_hdr->llh_cat_idx, llh->lgh_cur_idx, csi->csi_startcat, csi->csi_startidx); - if (rec->cr_index < csi->csi_startrec) + if (rec->cr.cr_index < csi->csi_startrec) /* Skip entries earlier than what we are interested in */ RETURN(0); - if (rec->cr_index == csi->csi_startrec) { + if (rec->cr.cr_index == csi->csi_startrec) { /* Remember where we started, since seq_read will re-read * the data when it reallocs space. Sigh, if only there was * a way to tell seq_file how big the buf should be in the @@ -2276,38 +2275,42 @@ static int changelog_show_cb(struct llog_handle *llh, struct llog_rec_hdr *hdr, /* Stop at some point with a reasonable seq_file buffer size. * Start from here the next time. */ - csi->csi_endrec = rec->cr_index - 1; + csi->csi_endrec = rec->cr.cr_index - 1; csi->csi_startcat = llh->lgh_hdr->llh_cat_idx; csi->csi_startidx = rec->cr_hdr.lrh_index - 1; csi->csi_wrote = 0; RETURN(LLOG_PROC_BREAK); } - rc = seq_printf(seq, LPU64" %02d%-5s "LPU64" 0x%x t="DFID, - rec->cr_index, rec->cr_type, - changelog_str[rec->cr_type], rec->cr_time, - rec->cr_flags & CLF_FLAGMASK, PFID(&rec->cr_tfid)); - - if (rec->cr_namelen) - /* namespace rec includes parent and filename */ - rc += seq_printf(seq, " p="DFID" %.*s\n", PFID(&rec->cr_pfid), - rec->cr_namelen, rec->cr_name); - else - rc += seq_puts(seq, "\n"); + CDEBUG(D_CHANGELOG, LPU64" %02d%-5s "LPU64" 0x%x t="DFID" p="DFID + " %.*s\n", rec->cr.cr_index, rec->cr.cr_type, + changelog_type2str(rec->cr.cr_type), rec->cr.cr_time, + rec->cr.cr_flags & CLF_FLAGMASK, + PFID(&rec->cr.cr_tfid), PFID(&rec->cr.cr_pfid), + rec->cr.cr_namelen, rec->cr.cr_name); + + cnt = sizeof(rec->cr) + rec->cr.cr_namelen; + ptr = (char *)(&rec->cr); + CDEBUG(D_CHANGELOG, "packed rec %d starting at %p\n", cnt, ptr); + rc = 0; + while ((cnt-- > 0) && (rc == 0)) { + rc = seq_putc(seq, *ptr); + ptr++; + } if (rc < 0) { /* Ran out of room in the seq buffer. seq_read will dump * the whole buffer and re-seq_start with a larger one; * no point in continuing the llog_process */ CDEBUG(D_CHANGELOG, "rec="LPU64" overflow "LPU64"<-"LPU64"\n", - rec->cr_index, csi->csi_startrec, csi->csi_endrec); + rec->cr.cr_index, csi->csi_startrec, csi->csi_endrec); csi->csi_endrec = csi->csi_startrec - 1; csi->csi_wrote = 0; RETURN(LLOG_PROC_BREAK); } csi->csi_wrote++; - csi->csi_endrec = rec->cr_index; + csi->csi_endrec = rec->cr.cr_index; RETURN(0); } diff --git a/lustre/ptlrpc/wiretest.c b/lustre/ptlrpc/wiretest.c index 4bd0158..790f861 100644 --- a/lustre/ptlrpc/wiretest.c +++ b/lustre/ptlrpc/wiretest.c @@ -1978,6 +1978,42 @@ void lustre_assert_wire_constants(void) LASSERTF((int)sizeof(((struct llog_size_change_rec *)0)->lsc_tail) == 8, " found %lld\n", (long long)(int)sizeof(((struct llog_size_change_rec *)0)->lsc_tail)); + /* Checks for struct changelog_rec */ + LASSERTF((int)sizeof(struct changelog_rec) == 64, " found %lld\n", + (long long)(int)sizeof(struct changelog_rec)); + LASSERTF((int)offsetof(struct changelog_rec, cr_namelen) == 0, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_namelen)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_namelen) == 2, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_namelen)); + LASSERTF((int)offsetof(struct changelog_rec, cr_flags) == 2, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_flags)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_flags) == 2, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_flags)); + LASSERTF((int)offsetof(struct changelog_rec, cr_type) == 4, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_type)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_type) == 4, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_type)); + LASSERTF((int)offsetof(struct changelog_rec, cr_index) == 8, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_index)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_index) == 8, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_index)); + LASSERTF((int)offsetof(struct changelog_rec, cr_prev) == 16, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_prev)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_prev) == 8, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_prev)); + LASSERTF((int)offsetof(struct changelog_rec, cr_time) == 24, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_time)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_time) == 8, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_time)); + LASSERTF((int)offsetof(struct changelog_rec, cr_tfid) == 32, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_tfid)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_tfid) == 16, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_tfid)); + LASSERTF((int)offsetof(struct changelog_rec, cr_pfid) == 48, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_pfid)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_pfid) == 16, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_pfid)); + /* Checks for struct llog_changelog_rec */ LASSERTF((int)sizeof(struct llog_changelog_rec) == 88, " found %lld\n", (long long)(int)sizeof(struct llog_changelog_rec)); @@ -1985,38 +2021,10 @@ void lustre_assert_wire_constants(void) (long long)(int)offsetof(struct llog_changelog_rec, cr_hdr)); LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_hdr) == 16, " found %lld\n", (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_hdr)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_flags) == 16, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_flags)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_flags) == 2, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_flags)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_namelen) == 18, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_namelen)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_namelen) == 2, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_namelen)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_type) == 20, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_type)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_type) == 4, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_type)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_index) == 24, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_index)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_index) == 8, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_index)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_prev) == 32, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_prev)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_prev) == 8, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_prev)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_time) == 40, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_time)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_time) == 8, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_time)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_tfid) == 48, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_tfid)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_tfid) == 16, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_tfid)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_pfid) == 64, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_pfid)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_pfid) == 16, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_pfid)); + LASSERTF((int)offsetof(struct llog_changelog_rec, cr) == 16, " found %lld\n", + (long long)(int)offsetof(struct llog_changelog_rec, cr)); + LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr) == 64, " found %lld\n", + (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr)); LASSERTF((int)offsetof(struct llog_changelog_rec, cr_tail) == 80, " found %lld\n", (long long)(int)offsetof(struct llog_changelog_rec, cr_tail)); LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_tail) == 8, " found %lld\n", diff --git a/lustre/utils/lfs.c b/lustre/utils/lfs.c index 38d074a..ba1306e 100644 --- a/lustre/utils/lfs.c +++ b/lustre/utils/lfs.c @@ -65,7 +65,6 @@ /* For dirname() */ #include -#include #include #include @@ -2359,58 +2358,18 @@ static int lfs_ls(int argc, char **argv) return(llapi_ls(argc, argv)); } -/* A helper function to return single, whole lines delimited by newline. - Returns length of line. Not reentrant! */ -static int get_next_full_line(int fd, char **ptr) -{ - static char buf[8192]; /* bigger than MAX_PATH_LENGTH */ - static char *sptr = buf, *eptr = buf; - static int len, rem; - - if ((*ptr == NULL) /* first time */ - || (eptr >= buf + len) /* buffer empty */) { - sptr = eptr = buf; - len = read(fd, buf, sizeof(buf)); - if (len <= 0) - return len; - } else { - sptr = eptr + 1; - } - -full_line: - while (eptr < buf + len) { - eptr++; - /* parse full lines */ - if (*eptr == '\n') { - *eptr = '\0'; - *ptr = sptr; - return (eptr - sptr); - } - } - - /* partial line; move to front of buf */ - rem = buf + len - sptr; - memcpy(buf, sptr, rem); - sptr = buf; - eptr = buf + rem; - len = read(fd, eptr, sizeof(buf) - rem); - if (len <= 0) - return len; - len += rem; - goto full_line; -} - static int lfs_changelog(int argc, char **argv) { - long long startrec = 0, endrec = 0, recnum; - int fd, len; - char c, *mdd, *ptr = NULL; + void *changelog_priv; + struct changelog_rec *rec; + long long startrec = 0, endrec = 0; + char c, *mdd; struct option long_opts[] = { {"follow", no_argument, 0, 'f'}, {0, 0, 0, 0} }; char short_opts[] = "f"; - int follow = 0; + int rc, follow = 0; optind = 0; while ((c = getopt_long(argc, argv, short_opts, @@ -2436,44 +2395,37 @@ static int lfs_changelog(int argc, char **argv) if (argc > optind) endrec = strtoll(argv[optind++], NULL, 10); - fd = llapi_changelog_open(mdd, startrec); - if (fd < 0) { - fprintf(stderr, "%s Can't open changelog: %s\n", argv[0], - strerror(errno = -fd)); - return fd; + rc = llapi_changelog_start(&changelog_priv, + follow ? CHANGELOG_FLAG_FOLLOW : 0, + mdd, startrec); + if (rc < 0) { + fprintf(stderr, "Can't start changelog: %s\n", + strerror(errno = -rc)); + return rc; } - while ((len = get_next_full_line(fd, &ptr)) >= 0) { - if (len == 0) { - struct pollfd pfds[1]; - int rc; - - if (!follow) - break; - pfds[0].fd = fd; - pfds[0].events = POLLIN; - rc = poll(pfds, 1, -1); - if (rc < 0) - break; - continue; - } - /* eg. 2 02MKDIR 4405821890 t=[0x100000400/0x5] p=[0x100000400/0x4] pics */ - sscanf(ptr, "%lld *", &recnum); - if (endrec && recnum > endrec) + while ((rc = llapi_changelog_recv(changelog_priv, &rec)) == 0) { + if (endrec && rec->cr_index > endrec) break; - if (recnum < startrec) + if (rec->cr_index < startrec) continue; - printf("%.*s\n", len, ptr); - } - close(fd); - - if (len < 0) { - fprintf(stderr, "read err %d\n", errno); - return -errno; + printf(LPU64" %02d%-5s "LPU64" 0x%x t="DFID, + rec->cr_index, rec->cr_type, + changelog_type2str(rec->cr_type), rec->cr_time, + rec->cr_flags & CLF_FLAGMASK, PFID(&rec->cr_tfid)); + if (rec->cr_namelen) + /* namespace rec includes parent and filename */ + printf(" p="DFID" %.*s\n", PFID(&rec->cr_pfid), + rec->cr_namelen, rec->cr_name); + else + printf("\n"); + llapi_changelog_free(&rec); } - return 0; + llapi_changelog_fini(&changelog_priv); + + return (rc == 1 ? 0 : rc); } static int lfs_changelog_clear(int argc, char **argv) diff --git a/lustre/utils/liblustreapi.c b/lustre/utils/liblustreapi.c index c029546..0164cd7 100644 --- a/lustre/utils/liblustreapi.c +++ b/lustre/utils/liblustreapi.c @@ -65,6 +65,7 @@ #else #include #endif +#include #include #include @@ -2441,18 +2442,23 @@ int llapi_ls(int argc, char *argv[]) /* Print mdtname 'name' into 'buf' using 'format'. Add -MDT0000 if needed. * format must have %s%s, buf must be > 16 */ -static int get_mdtname(const char *name, char *format, char *buf) +static int get_mdtname(char *name, char *format, char *buf) { char suffix[]="-MDT0000"; int len = strlen(name); + if ((len > 5) && (strncmp(name + len - 5, "_UUID", 5) == 0)) { + name[len - 5] = '\0'; + len -= 5; + } + if (len > 8) { if ((len <= 16) && strncmp(name + len - 8, "-MDT", 4) == 0) { suffix[0] = '\0'; } else { /* Not enough room to add suffix */ - llapi_err(LLAPI_MSG_ERROR, "MDT name too long |%s|\n", - name); + llapi_err(LLAPI_MSG_ERROR | LLAPI_MSG_NO_ERRNO, + "MDT name too long |%s|", name); return -EINVAL; } } @@ -2460,12 +2466,26 @@ static int get_mdtname(const char *name, char *format, char *buf) return sprintf(buf, format, name, suffix); } +/****** Changelog API ********/ +#define CHANGELOG_PRIV_MAGIC 0xCA8E1080 +struct changelog_private { + int magic; + int fd; + int flags; +}; -/* Return a file descriptor to a readable changelog */ -int llapi_changelog_open(const char *device, long long startrec) +/** Start reading from a changelog + * @param priv Opaque private control structure + * @param flags Start flags (e.g. follow) + * @param device Report changes recorded on this MDT + * @param startrec Report changes beginning with this record number + */ +int llapi_changelog_start(void **priv, int flags, const char *device, + long long startrec) { + struct changelog_private *cp; char path[256]; - char mdtname[17]; + char mdtname[20]; int rc, fd; if (device[0] == '/') @@ -2493,7 +2513,99 @@ int llapi_changelog_open(const char *device, long long startrec) return -errno; } - return fd; + cp = malloc(sizeof(*cp)); + if (cp == NULL) { + close(fd); + return -ENOMEM; + } + + cp->magic = CHANGELOG_PRIV_MAGIC; + cp->fd = fd; + cp->flags = flags; + *priv = cp; + + return 0; +} + +/** Finish reading from a changelog */ +int llapi_changelog_fini(void **priv) +{ + struct changelog_private *cp = (struct changelog_private *)*priv; + + if (!cp || (cp->magic != CHANGELOG_PRIV_MAGIC)) + return -EINVAL; + + close(cp->fd); + free(cp); + *priv = NULL; + return 0; +} + +static int pollwait(int fd) { + struct pollfd pfds[1]; + int rc; + + pfds[0].fd = fd; + pfds[0].events = POLLIN; + rc = poll(pfds, 1, -1); + return rc < 0 ? -errno : rc; +} + +/** Read the next changelog entry + * @param priv Opaque private control structure + * @param rech Changelog record handle; record will be allocated here + * @return 0 valid message received; rec is set + * <0 error code + * 1 EOF + */ +int llapi_changelog_recv(void *priv, struct changelog_rec **rech) +{ + struct changelog_private *cp = (struct changelog_private *)priv; + struct changelog_rec rec, *recp; + int rc = 0; + + if (!cp || (cp->magic != CHANGELOG_PRIV_MAGIC)) + return -EINVAL; + if (rech == NULL) + return -EINVAL; + +readrec: + /* Read in the rec to get the namelen */ + rc = read(cp->fd, &rec, sizeof(rec)); + if (rc < 0) + return -errno; + if (rc == 0) { + if (cp->flags && CHANGELOG_FLAG_FOLLOW) { + rc = pollwait(cp->fd); + if (rc < 0) + return rc; + goto readrec; + } + return 1; + } + + recp = malloc(sizeof(rec) + rec.cr_namelen); + if (recp == NULL) + return -ENOMEM; + memcpy(recp, &rec, sizeof(rec)); + rc = read(cp->fd, recp->cr_name, rec.cr_namelen); + if (rc < 0) { + free(recp); + llapi_err(LLAPI_MSG_ERROR, "Can't read entire filename"); + return -errno; + } + + *rech = recp; + return 0; +} + +/** Release the changelog record when done with it. */ +int llapi_changelog_free(struct changelog_rec **rech) +{ + if (*rech) + free(*rech); + *rech = NULL; + return 0; } int llapi_changelog_clear(const char *mdtname, const char *idstr, @@ -2525,7 +2637,7 @@ int llapi_changelog_clear(const char *mdtname, const char *idstr, fd = open(mdtname, O_RDONLY | O_DIRECTORY | O_NONBLOCK); rc = fd < 0 ? -errno : 0; } else { - if (get_mdtname(mdtname, "%s%s", fsname) < 0) + if (get_mdtname((char *)mdtname, "%s%s", fsname) < 0) return -EINVAL; ptr = fsname + strlen(fsname) - 8; *ptr = '\0'; diff --git a/lustre/utils/lreplicate.c b/lustre/utils/lreplicate.c index b1b64e4..c4ee8f8 100644 --- a/lustre/utils/lreplicate.c +++ b/lustre/utils/lreplicate.c @@ -518,7 +518,7 @@ void lr_get_FID_PATH(char *mntpt, char *fidstr, char *buf, int bufsize) { /* Open-by-FID path is /.lustre/fid/[SEQ:OID:VER] */ snprintf(buf, bufsize, "%s/%s/fid/%s", mntpt, dot_lustre_name, - fidstr + 2); + fidstr); return; } @@ -610,8 +610,8 @@ int lr_add_pc(const char *pfid, const char *tfid, const char *name) p = calloc(1, sizeof(*p)); if (!p) return -ENOMEM; - strcpy(p->pc_log.pcl_pfid, pfid + 2); - strcpy(p->pc_log.pcl_tfid, tfid + 2); + strcpy(p->pc_log.pcl_pfid, pfid); + strcpy(p->pc_log.pcl_tfid, tfid); strcpy(p->pc_log.pcl_name, name); p->pc_next = parents; @@ -664,8 +664,8 @@ int lr_remove_pc(const char *pfid, const char *tfid) struct lr_parent_child_list *curr, *prev; for (prev = curr = parents; curr; prev = curr, curr = curr->pc_next) { - if (strcmp(curr->pc_log.pcl_pfid, pfid + 2) == 0 && - strcmp(curr->pc_log.pcl_tfid, tfid + 2) == 0) { + if (strcmp(curr->pc_log.pcl_pfid, pfid) == 0 && + strcmp(curr->pc_log.pcl_tfid, tfid) == 0) { if (curr == parents) parents = curr->pc_next; else @@ -684,7 +684,7 @@ int lr_mk_special(struct lr_info *info) snprintf(info->dest, PATH_MAX, "%s/%s/%s", status->ls_targets[info->target_no], SPECIAL_DIR, - info->tfid + 2); + info->tfid); rc = lr_mkfile(info); if (rc) @@ -715,7 +715,7 @@ int lr_rm_special(struct lr_info *info) snprintf(info->dest, PATH_MAX, "%s/%s/%s", status->ls_targets[info->target_no], SPECIAL_DIR, - info->tfid + 2); + info->tfid); rc = lr_rmfile(info); if (rc) @@ -733,7 +733,7 @@ int lr_create(struct lr_info *info) int mkspecial = 0; /* Is target FID present on the source? */ - rc = lr_get_path(info, info->tfid + 3); + rc = lr_get_path(info, info->tfid); if (rc == -ENOENT) { /* Source file has disappeared. Not an error. */ lr_debug(DINFO, "create: tfid %s not found on" @@ -745,7 +745,7 @@ int lr_create(struct lr_info *info) strcpy(info->savedpath, info->path); /* Is parent FID present on the source */ - rc = lr_get_path(info, info->pfid + 3); + rc = lr_get_path(info, info->pfid); if (rc == -ENOENT) { lr_debug(DINFO, "create: pfid %s not found on source-fs\n", info->tfid); @@ -808,7 +808,7 @@ int lr_remove(struct lr_info *info) if (!rc1) continue; - rc1 = lr_get_path(info, info->pfid + 3); + rc1 = lr_get_path(info, info->pfid); if (rc1 == -ENOENT) { lr_debug(DINFO, "remove: pfid %s not found\n", info->pfid); @@ -843,11 +843,11 @@ int lr_move(struct lr_info *info, struct lr_info *ext) int special_src = 0; int special_dest = 0; - rc_dest = lr_get_path(ext, ext->pfid + 3); + rc_dest = lr_get_path(ext, ext->pfid); if (rc_dest < 0 && rc_dest != -ENOENT) return rc_dest; - rc_src = lr_get_path(info, info->pfid + 3); + rc_src = lr_get_path(info, info->pfid); if (rc_src < 0 && rc_src != -ENOENT) return rc_src; @@ -869,7 +869,7 @@ int lr_move(struct lr_info *info, struct lr_info *ext) if (rc_dest == -ENOENT) { snprintf(info->dest, PATH_MAX, "%s/%s/%s", status->ls_targets[info->target_no], - SPECIAL_DIR, info->tfid + 2); + SPECIAL_DIR, info->tfid); special_dest = 1; } @@ -881,7 +881,7 @@ int lr_move(struct lr_info *info, struct lr_info *ext) errno == ENOENT)) { snprintf(info->src, PATH_MAX, "%s/%s/%s", status->ls_targets[info->target_no], - SPECIAL_DIR, info->tfid + 2); + SPECIAL_DIR, info->tfid); special_src = 1; } @@ -895,7 +895,7 @@ int lr_move(struct lr_info *info, struct lr_info *ext) if (special_src) { lr_remove_pc(info->pfid, info->tfid); if (!special_dest) - lr_cascade_move(info->tfid + 2, info->dest, info); + lr_cascade_move(info->tfid, info->dest, info); } if (special_dest) lr_add_pc(ext->pfid, info->tfid, ext->name); @@ -932,7 +932,7 @@ int lr_link(struct lr_info *info) /* Search through the hardlinks to get the src and dest */ for (i = 0; i < st.st_nlink && (info->src[0] == 0 || info->dest[0] == 0); i++) { - rc1 = lr_get_path_ln(info, info->tfid + 3, i); + rc1 = lr_get_path_ln(info, info->tfid, i); lr_debug(rc1 ? 0:DTRACE, "\tfid2path %s, %s, %d rc=%d\n", info->path, info->name, i, rc1); if (rc1) @@ -964,11 +964,11 @@ int lr_link(struct lr_info *info) if (info->src[0] == 0) snprintf(info->src, PATH_MAX, "%s/%s/%s", status->ls_targets[info->target_no], - SPECIAL_DIR, info->tfid + 2); + SPECIAL_DIR, info->tfid); else if (info->dest[0] == 0) snprintf(info->dest, PATH_MAX, "%s/%s/%s", status->ls_targets[info->target_no], - SPECIAL_DIR, info->tfid + 2); + SPECIAL_DIR, info->tfid); rc1 = link(info->src, info->dest); lr_debug(rc1?0:DINFO, "link: %s [to] %s; rc1=%d %s\n", @@ -988,7 +988,7 @@ int lr_setattr(struct lr_info *info) lr_get_FID_PATH(status->ls_source, info->tfid, info->src, PATH_MAX); - rc = lr_get_path(info, info->tfid + 3); + rc = lr_get_path(info, info->tfid); if (rc == -ENOENT) lr_debug(DINFO, "setattr: %s not present on source-fs\n", info->src); @@ -1019,7 +1019,7 @@ int lr_setxattr(struct lr_info *info) lr_get_FID_PATH(status->ls_source, info->tfid, info->src, PATH_MAX); - rc = lr_get_path(info, info->tfid + 3); + rc = lr_get_path(info, info->tfid); if (rc == -ENOENT) lr_debug(DINFO, "setxattr: %s not present on source-fs\n", info->src); @@ -1043,51 +1043,23 @@ int lr_setxattr(struct lr_info *info) } /* Parse a line of changelog entry */ -int lr_parse_line(struct lr_info *info, FILE *fp) +int lr_parse_line(void *priv, struct lr_info *info) { - unsigned long long time; - unsigned int flags; - char typestr[TYPE_STR_LEN]; - char line[PATH_MAX]; - char *str; - int i; + struct changelog_rec *rec; - if (fgets(line, sizeof(line), fp) != NULL) { - if (sscanf(line, "%llu %s %llu %x %s %s", - &info->recno, typestr, &time, - &flags, info->tfid, info->pfid) < 4) { - fprintf(stderr, "error: unexpected changelog record " - "format - %s\n", line); - return -1; - } - typestr[2] = '\0'; - info->type = atoi(typestr); - - /* The filename could have spaces in it. scanf would - have ignored it. Parse for the complete - filename. */ - if (info->type != CL_SETATTR && - info->type != CL_XATTR && - info->type != CL_MARK) { - for (i = 0, str = line; str != NULL && i <= 5; - i++, str++){ - str = strchr(str, ' '); - } - if (str) { - strncpy(info->name, str, PATH_MAX); - str = strchr(info->name, '\n'); - if (str) - str[0] = '\0'; - } else { - fprintf(stderr, "error: unexpected changelog " - "record format - %s\n", line); - return -1; - } - } - rec_count++; - } else { + if (llapi_changelog_recv(priv, &rec) != 0) return -1; - } + + info->recno = rec->cr_index; + info->type = rec->cr_type; + sprintf(info->tfid, DFID, PFID(&rec->cr_tfid)); + sprintf(info->pfid, DFID, PFID(&rec->cr_pfid)); + strncpy(info->name, rec->cr_name, rec->cr_namelen); + info->name[rec->cr_namelen] = '\0'; + + llapi_changelog_free(&rec); + + rec_count++; return 0; } @@ -1352,22 +1324,18 @@ void lr_print_status(struct lr_info *info) printf("Using rsync: %s (%s)\n", rsync, rsync_ver); } -DECLARE_CHANGELOG_NAMES; - void lr_print_failure(struct lr_info *info, int rc) { fprintf(stderr, "Replication of operation failed(%d):" - " %lld %s (%d) %s %s %s\n", rc, info->recno, - changelog_str[info->type], info->type, info->tfid, + " %lld %s (%d) %s %s %s\n", rc, info->recno, + changelog_type2str(info->type), info->type, info->tfid, info->pfid, info->name); } /* Replicate filesystem operations from src_path to target_path */ int lr_replicate() { - int fd; - FILE *fp; - long long startrec; + void *changelog_priv; struct lr_info *info; struct lr_info *ext; time_t start; @@ -1419,25 +1387,20 @@ int lr_replicate() lr_print_status(info); /* Open changelogs for consumption*/ - startrec = status->ls_last_recno; - fd = llapi_changelog_open(status->ls_source_fs, startrec); - if (fd < 0) { + rc = llapi_changelog_start(&changelog_priv, 0, status->ls_source_fs, + status->ls_last_recno); + if (rc < 0) { fprintf(stderr, "Error opening changelog file for fs %s.\n", status->ls_source_fs); - return fd; - } - if ((fp = fdopen(fd, "r")) == NULL) { - fprintf(stderr, "Error: fdopen failed."); - close(fd); - return -errno; + return rc; } - while (!quit && lr_parse_line(info, fp) == 0) { + while (!quit && lr_parse_line(changelog_priv, info) == 0) { rc = 0; if (info->type == CL_RENAME) /* Rename operations have an additional changelog record of information. */ - lr_parse_line(ext, fp); + lr_parse_line(changelog_priv, ext); if (dryrun) continue; @@ -1488,6 +1451,8 @@ int lr_replicate() } } + llapi_changelog_fini(&changelog_priv); + if (errors || verbose) printf("Errors: %d\n", errors); @@ -1499,9 +1464,6 @@ int lr_replicate() printf("Changelog records consumed: %lld\n", rec_count); } - close(fd); - fclose(fp); - return 0; } diff --git a/lustre/utils/wirecheck.c b/lustre/utils/wirecheck.c index c68650c..99543bd 100644 --- a/lustre/utils/wirecheck.c +++ b/lustre/utils/wirecheck.c @@ -956,19 +956,27 @@ check_llog_size_change_rec(void) } static void +check_changelog_rec(void) +{ + BLANK_LINE(); + CHECK_STRUCT(changelog_rec); + CHECK_MEMBER(changelog_rec, cr_namelen); + CHECK_MEMBER(changelog_rec, cr_flags); + CHECK_MEMBER(changelog_rec, cr_type); + CHECK_MEMBER(changelog_rec, cr_index); + CHECK_MEMBER(changelog_rec, cr_prev); + CHECK_MEMBER(changelog_rec, cr_time); + CHECK_MEMBER(changelog_rec, cr_tfid); + CHECK_MEMBER(changelog_rec, cr_pfid); +} + +static void check_llog_changelog_rec(void) { BLANK_LINE(); CHECK_STRUCT(llog_changelog_rec); CHECK_MEMBER(llog_changelog_rec, cr_hdr); - CHECK_MEMBER(llog_changelog_rec, cr_flags); - CHECK_MEMBER(llog_changelog_rec, cr_namelen); - CHECK_MEMBER(llog_changelog_rec, cr_type); - CHECK_MEMBER(llog_changelog_rec, cr_index); - CHECK_MEMBER(llog_changelog_rec, cr_prev); - CHECK_MEMBER(llog_changelog_rec, cr_time); - CHECK_MEMBER(llog_changelog_rec, cr_tfid); - CHECK_MEMBER(llog_changelog_rec, cr_pfid); + CHECK_MEMBER(llog_changelog_rec, cr); CHECK_MEMBER(llog_changelog_rec, cr_tail); } @@ -1465,6 +1473,7 @@ main(int argc, char **argv) check_llog_setattr_rec(); check_llog_setattr64_rec(); check_llog_size_change_rec(); + check_changelog_rec(); check_llog_changelog_rec(); check_llog_gen(); check_llog_gen_rec(); diff --git a/lustre/utils/wiretest.c b/lustre/utils/wiretest.c index 697f917..bebd1f4b 100644 --- a/lustre/utils/wiretest.c +++ b/lustre/utils/wiretest.c @@ -1975,6 +1975,42 @@ void lustre_assert_wire_constants(void) LASSERTF((int)sizeof(((struct llog_size_change_rec *)0)->lsc_tail) == 8, " found %lld\n", (long long)(int)sizeof(((struct llog_size_change_rec *)0)->lsc_tail)); + /* Checks for struct changelog_rec */ + LASSERTF((int)sizeof(struct changelog_rec) == 64, " found %lld\n", + (long long)(int)sizeof(struct changelog_rec)); + LASSERTF((int)offsetof(struct changelog_rec, cr_namelen) == 0, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_namelen)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_namelen) == 2, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_namelen)); + LASSERTF((int)offsetof(struct changelog_rec, cr_flags) == 2, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_flags)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_flags) == 2, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_flags)); + LASSERTF((int)offsetof(struct changelog_rec, cr_type) == 4, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_type)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_type) == 4, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_type)); + LASSERTF((int)offsetof(struct changelog_rec, cr_index) == 8, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_index)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_index) == 8, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_index)); + LASSERTF((int)offsetof(struct changelog_rec, cr_prev) == 16, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_prev)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_prev) == 8, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_prev)); + LASSERTF((int)offsetof(struct changelog_rec, cr_time) == 24, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_time)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_time) == 8, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_time)); + LASSERTF((int)offsetof(struct changelog_rec, cr_tfid) == 32, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_tfid)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_tfid) == 16, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_tfid)); + LASSERTF((int)offsetof(struct changelog_rec, cr_pfid) == 48, " found %lld\n", + (long long)(int)offsetof(struct changelog_rec, cr_pfid)); + LASSERTF((int)sizeof(((struct changelog_rec *)0)->cr_pfid) == 16, " found %lld\n", + (long long)(int)sizeof(((struct changelog_rec *)0)->cr_pfid)); + /* Checks for struct llog_changelog_rec */ LASSERTF((int)sizeof(struct llog_changelog_rec) == 88, " found %lld\n", (long long)(int)sizeof(struct llog_changelog_rec)); @@ -1982,38 +2018,10 @@ void lustre_assert_wire_constants(void) (long long)(int)offsetof(struct llog_changelog_rec, cr_hdr)); LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_hdr) == 16, " found %lld\n", (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_hdr)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_flags) == 16, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_flags)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_flags) == 2, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_flags)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_namelen) == 18, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_namelen)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_namelen) == 2, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_namelen)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_type) == 20, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_type)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_type) == 4, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_type)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_index) == 24, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_index)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_index) == 8, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_index)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_prev) == 32, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_prev)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_prev) == 8, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_prev)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_time) == 40, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_time)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_time) == 8, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_time)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_tfid) == 48, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_tfid)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_tfid) == 16, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_tfid)); - LASSERTF((int)offsetof(struct llog_changelog_rec, cr_pfid) == 64, " found %lld\n", - (long long)(int)offsetof(struct llog_changelog_rec, cr_pfid)); - LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_pfid) == 16, " found %lld\n", - (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr_pfid)); + LASSERTF((int)offsetof(struct llog_changelog_rec, cr) == 16, " found %lld\n", + (long long)(int)offsetof(struct llog_changelog_rec, cr)); + LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr) == 64, " found %lld\n", + (long long)(int)sizeof(((struct llog_changelog_rec *)0)->cr)); LASSERTF((int)offsetof(struct llog_changelog_rec, cr_tail) == 80, " found %lld\n", (long long)(int)offsetof(struct llog_changelog_rec, cr_tail)); LASSERTF((int)sizeof(((struct llog_changelog_rec *)0)->cr_tail) == 8, " found %lld\n", -- 1.8.3.1