X-Git-Url: https://git.whamcloud.com/?p=fs%2Flustre-release.git;a=blobdiff_plain;f=lustre%2Finclude%2Flustre%2Flustre_idl.h;h=8226334e6a4f09e0ef30ac435eab27bb5b374e17;hp=a139e998998c43cec977c89024557af501023e22;hb=c961228f1c30254c454ed1432ba83af3aa7c39b4;hpb=3bb8d1b9656994b0313cdba6ad8eeb7b84f5ee9f diff --git a/lustre/include/lustre/lustre_idl.h b/lustre/include/lustre/lustre_idl.h index a139e998..8226334 100644 --- a/lustre/include/lustre/lustre_idl.h +++ b/lustre/include/lustre/lustre_idl.h @@ -1,6 +1,4 @@ -/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*- - * vim:expandtab:shiftwidth=8:tabstop=8: - * +/* * GPL HEADER START * * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. @@ -28,6 +26,8 @@ /* * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved. * Use is subject to license terms. + * + * Copyright (c) 2011, 2012, Intel Corporation. */ /* * This file is part of Lustre, http://www.lustre.org/ @@ -91,7 +91,9 @@ #ifndef _LUSTRE_IDL_H_ #define _LUSTRE_IDL_H_ +#if !defined(LASSERT) && !defined(LPU64) #include /* for LASSERT, LPUX64, etc */ +#endif /* Defn's shared with user-space. */ #include @@ -137,6 +139,7 @@ #define SEQ_METADATA_PORTAL 30 #define SEQ_DATA_PORTAL 31 #define SEQ_CONTROLLER_PORTAL 32 +#define MGS_BULK_PORTAL 33 /* Portal 63 is reserved for the Cray Inc DVS - nic@cray.com, roe@cray.com, n8851@cray.com */ @@ -248,19 +251,22 @@ static inline int range_compare_loc(const struct lu_seq_range *r1, r1->lsr_flags != r2->lsr_flags; } -#define DRANGE "[%#16.16"LPF64"x-%#16.16"LPF64"x):%x:%x" +#define DRANGE "[%#16.16"LPF64"x-%#16.16"LPF64"x):%x:%s" #define PRANGE(range) \ - (range)->lsr_start, \ - (range)->lsr_end, \ - (range)->lsr_index, \ - (range)->lsr_flags + (range)->lsr_start, \ + (range)->lsr_end, \ + (range)->lsr_index, \ + (range)->lsr_flags == LU_SEQ_RANGE_MDT ? "mdt" : "ost" + /** \defgroup lu_fid lu_fid * @{ */ /** * Flags for lustre_mdt_attrs::lma_compat and lustre_mdt_attrs::lma_incompat. + * Deprecated since HSM and SOM attributes are now stored in separate on-disk + * xattr. */ enum lma_compat { LMAC_HSM = 0x00000001, @@ -271,9 +277,10 @@ enum lma_compat { * Masks for all features that should be supported by a Lustre version to * access a specific file. * This information is stored in lustre_mdt_attrs::lma_incompat. - * - * NOTE: No incompat feature should be added before bug #17670 is landed. */ +enum lma_incompat { + LMAI_RELEASED = 0x0000001, /* file is released */ +}; #define LMA_INCOMPAT_SUPP 0x0 /** @@ -296,66 +303,56 @@ struct lustre_mdt_attrs { struct lu_fid lma_self_fid; /** mdt/ost type, others */ __u64 lma_flags; - /* IO Epoch SOM attributes belongs to */ - __u64 lma_ioepoch; - /** total file size in objects */ - __u64 lma_som_size; - /** total fs blocks in objects */ - __u64 lma_som_blocks; - /** mds mount id the size is valid for */ - __u64 lma_som_mountid; }; /** - * Fill \a lma with its first content. - * Only fid is stored. + * Prior to 2.4, the LMA structure also included SOM attributes which has since + * been moved to a dedicated xattr */ -static inline void lustre_lma_init(struct lustre_mdt_attrs *lma, - const struct lu_fid *fid) -{ - lma->lma_compat = 0; - lma->lma_incompat = 0; - memcpy(&lma->lma_self_fid, fid, sizeof(*fid)); - lma->lma_flags = 0; - lma->lma_ioepoch = 0; - lma->lma_som_size = 0; - lma->lma_som_blocks = 0; - lma->lma_som_mountid = 0; +#define LMA_OLD_SIZE (sizeof(struct lustre_mdt_attrs) + 4 * sizeof(__u64)) + +extern void lustre_lma_swab(struct lustre_mdt_attrs *lma); +extern void lustre_lma_init(struct lustre_mdt_attrs *lma, + const struct lu_fid *fid); +/** + * SOM on-disk attributes stored in a separate xattr. + */ +struct som_attrs { + /** Bitfield for supported data in this structure. For future use. */ + __u32 som_compat; + + /** Incompat feature list. The supported feature mask is availabe in + * SOM_INCOMPAT_SUPP */ + __u32 som_incompat; - /* If a field is added in struct lustre_mdt_attrs, zero it explicitly - * and change the test below. */ - LASSERT(sizeof(*lma) == - (offsetof(struct lustre_mdt_attrs, lma_som_mountid) + - sizeof(lma->lma_som_mountid))); + /** IO Epoch SOM attributes belongs to */ + __u64 som_ioepoch; + /** total file size in objects */ + __u64 som_size; + /** total fs blocks in objects */ + __u64 som_blocks; + /** mds mount id the size is valid for */ + __u64 som_mountid; }; +extern void lustre_som_swab(struct som_attrs *attrs); -extern void lustre_swab_lu_fid(struct lu_fid *fid); +#define SOM_INCOMPAT_SUPP 0x0 /** - * Swab, if needed, lustre_mdt_attr struct to on-disk format. - * Otherwise, do not touch it. + * HSM on-disk attributes stored in a separate xattr. */ -static inline void lustre_lma_swab(struct lustre_mdt_attrs *lma) -{ - /* Use LUSTRE_MSG_MAGIC to detect local endianess. */ - if (LUSTRE_MSG_MAGIC != cpu_to_le32(LUSTRE_MSG_MAGIC)) { - __swab32s(&lma->lma_compat); - __swab32s(&lma->lma_incompat); - lustre_swab_lu_fid(&lma->lma_self_fid); - __swab64s(&lma->lma_flags); - __swab64s(&lma->lma_ioepoch); - __swab64s(&lma->lma_som_size); - __swab64s(&lma->lma_som_blocks); - __swab64s(&lma->lma_som_mountid); - } -}; - -/* This is the maximum number of MDTs allowed in CMD testing until such - * a time that FID-on-OST is implemented. This is due to the limitations - * of packing non-0-MDT numbers into the FID SEQ namespace. Once FID-on-OST - * is implemented this limit will be virtually unlimited. */ -#define MAX_MDT_COUNT 8 +struct hsm_attrs { + /** Bitfield for supported data in this structure. For future use. */ + __u32 hsm_compat; + /** HSM flags, see hsm_flags enum below */ + __u32 hsm_flags; + /** backend archive id associated with the file */ + __u64 hsm_arch_id; + /** version associated with the last archiving, if any */ + __u64 hsm_arch_ver; +}; +extern void lustre_hsm_swab(struct hsm_attrs *attrs); /** * fid constants @@ -414,9 +411,17 @@ enum fid_seq { FID_SEQ_IDIF_MAX = 0x1ffffffffULL, /* Normal FID sequence starts from this value, i.e. 1<<33 */ FID_SEQ_START = 0x200000000ULL, + /* sequence for local pre-defined FIDs listed in local_oid */ FID_SEQ_LOCAL_FILE = 0x200000001ULL, FID_SEQ_DOT_LUSTRE = 0x200000002ULL, - FID_SEQ_NORMAL = 0x200000400ULL + /* sequence is used for local named objects FIDs generated + * by local_object_storage library */ + FID_SEQ_LOCAL_NAME = 0x200000003ULL, + FID_SEQ_SPECIAL = 0x200000004ULL, + FID_SEQ_QUOTA = 0x200000005ULL, + FID_SEQ_QUOTA_GLB = 0x200000006ULL, + FID_SEQ_NORMAL = 0x200000400ULL, + FID_SEQ_LOV_DEFAULT= 0xffffffffffffffffULL }; #define OBIF_OID_MAX_BITS 32 @@ -426,26 +431,51 @@ enum fid_seq { #define IDIF_MAX_OID (1ULL << IDIF_OID_MAX_BITS) #define IDIF_OID_MASK ((1ULL << IDIF_OID_MAX_BITS) - 1) +/** OID for FID_SEQ_SPECIAL */ +enum special_oid { + /* Big Filesystem Lock to serialize rename operations */ + FID_OID_SPECIAL_BFL = 1UL, +}; + +/** OID for FID_SEQ_DOT_LUSTRE */ +enum dot_lustre_oid { + FID_OID_DOT_LUSTRE = 1UL, + FID_OID_DOT_LUSTRE_OBF = 2UL, +}; static inline int fid_seq_is_mdt0(obd_seq seq) { return (seq == FID_SEQ_OST_MDT0); } -static inline int fid_seq_is_cmd(const __u64 seq) +static inline int fid_seq_is_mdt(const __u64 seq) { - return (seq >= FID_SEQ_OST_MDT1 && seq <= FID_SEQ_OST_MAX); + return seq == FID_SEQ_OST_MDT0 || seq >= FID_SEQ_NORMAL; }; -static inline int fid_seq_is_mdt(const __u64 seq) +static inline int fid_seq_is_echo(obd_seq seq) { - return seq == FID_SEQ_OST_MDT0 || - (seq >= FID_SEQ_OST_MDT1 && seq <= FID_SEQ_OST_MAX); -}; + return (seq == FID_SEQ_ECHO); +} + +static inline int fid_is_echo(const struct lu_fid *fid) +{ + return fid_seq_is_echo(fid_seq(fid)); +} + +static inline int fid_seq_is_llog(obd_seq seq) +{ + return (seq == FID_SEQ_LLOG); +} + +static inline int fid_is_llog(const struct lu_fid *fid) +{ + return fid_seq_is_llog(fid_seq(fid)); +} static inline int fid_seq_is_rsvd(const __u64 seq) { - return seq <= FID_SEQ_RSVD; + return (seq > FID_SEQ_OST_MDT0 && seq <= FID_SEQ_RSVD); }; static inline int fid_is_mdt0(const struct lu_fid *fid) @@ -510,6 +540,13 @@ static inline obd_id fid_idif_id(obd_seq seq, __u32 oid, __u32 ver) return ((__u64)ver << 48) | ((seq & 0xffff) << 32) | oid; } +/* extract ost index from IDIF FID */ +static inline __u32 fid_idif_ost_idx(const struct lu_fid *fid) +{ + LASSERT(fid_is_idif(fid)); + return (fid_seq(fid) >> 16) & 0xffff; +} + /* unpack an ostid (id/seq) from a wire/disk structure into an IDIF FID */ static inline void ostid_idif_unpack(struct ost_id *ostid, struct lu_fid *fid, __u32 ost_idx) @@ -589,21 +626,24 @@ static inline int fid_ostid_unpack(struct lu_fid *fid, struct ost_id *ostid, } /* pack an IDIF FID into an ostid (id/seq) for the wire/disk */ -static inline void ostid_idif_pack(struct lu_fid *fid, struct ost_id *ostid) +static inline void ostid_idif_pack(const struct lu_fid *fid, + struct ost_id *ostid) { ostid->oi_seq = FID_SEQ_OST_MDT0; ostid->oi_id = fid_idif_id(fid->f_seq, fid->f_oid, fid->f_ver); } /* pack a non-IDIF FID into an ostid (id/seq) for the wire/disk */ -static inline void ostid_fid_pack(struct lu_fid *fid, struct ost_id *ostid) +static inline void ostid_fid_pack(const struct lu_fid *fid, + struct ost_id *ostid) { ostid->oi_seq = fid_seq(fid); ostid->oi_id = fid_ver_oid(fid); } /* pack any OST FID into an ostid (id/seq) for the wire/disk */ -static inline int fid_ostid_pack(struct lu_fid *fid, struct ost_id *ostid) +static inline int fid_ostid_pack(const struct lu_fid *fid, + struct ost_id *ostid) { if (unlikely(fid_seq_is_igif(fid->f_seq))) { CERROR("bad IGIF, "DFID"\n", PFID(fid)); @@ -646,6 +686,13 @@ static inline obd_id ostid_id(struct ost_id *ostid) return ostid->oi_id; } +/* Check whether the fid is for LAST_ID */ +static inline int fid_is_last_id(const struct lu_fid *fid) +{ + return (fid_is_idif(fid) || fid_is_norm(fid) || fid_is_echo(fid)) && + fid_oid(fid) == 0; +} + /** * Get inode number from a igif. * \param fid a igif to get inode number from. @@ -657,21 +704,6 @@ static inline ino_t lu_igif_ino(const struct lu_fid *fid) } /** - * Build igif from the inode number/generation. - */ -#define LU_IGIF_BUILD(fid, ino, gen) \ -do { \ - fid->f_seq = ino; \ - fid->f_oid = gen; \ - fid->f_ver = 0; \ -} while(0) -static inline void lu_igif_build(struct lu_fid *fid, __u32 ino, __u32 gen) -{ - LU_IGIF_BUILD(fid, ino, gen); - LASSERT(fid_is_igif(fid)); -} - -/** * Get inode generation from a igif. * \param fid a igif to get inode generation from. * \return inode generation for the igif. @@ -681,6 +713,16 @@ static inline __u32 lu_igif_gen(const struct lu_fid *fid) return fid_oid(fid); } +/** + * Build igif from the inode number/generation. + */ +static inline void lu_igif_build(struct lu_fid *fid, __u32 ino, __u32 gen) +{ + fid->f_seq = ino; + fid->f_oid = gen; + fid->f_ver = 0; +} + /* * Fids are transmitted across network (in the sender byte-ordering), * and stored on disk in big-endian order. @@ -735,11 +777,10 @@ static inline void fid_be_to_cpu(struct lu_fid *dst, const struct lu_fid *src) static inline int fid_is_sane(const struct lu_fid *fid) { - return - fid != NULL && - ((fid_seq(fid) >= FID_SEQ_START && fid_oid(fid) != 0 - && fid_ver(fid) == 0) || - fid_is_igif(fid)); + return fid != NULL && + ((fid_seq(fid) >= FID_SEQ_START && fid_ver(fid) == 0) || + fid_is_igif(fid) || fid_is_idif(fid) || + fid_seq_is_rsvd(fid_seq(fid))); } static inline int fid_is_zero(const struct lu_fid *fid) @@ -756,8 +797,10 @@ static inline int lu_fid_eq(const struct lu_fid *f0, /* Check that there is no alignment padding. */ CLASSERT(sizeof *f0 == sizeof f0->f_seq + sizeof f0->f_oid + sizeof f0->f_ver); - LASSERTF(fid_is_igif(f0) || fid_ver(f0) == 0, DFID, PFID(f0)); - LASSERTF(fid_is_igif(f1) || fid_ver(f1) == 0, DFID, PFID(f1)); + LASSERTF((fid_is_igif(f0) || fid_is_idif(f0)) || + fid_ver(f0) == 0, DFID, PFID(f0)); + LASSERTF((fid_is_igif(f1) || fid_is_idif(f1)) || + fid_ver(f1) == 0, DFID, PFID(f1)); return memcmp(f0, f1, sizeof *f0) == 0; } @@ -790,10 +833,27 @@ static inline int lu_fid_cmp(const struct lu_fid *f0, * enumeration. */ enum lu_dirent_attrs { - LUDA_FID = 0x0001, - LUDA_TYPE = 0x0002, + LUDA_FID = 0x0001, + LUDA_TYPE = 0x0002, + LUDA_64BITHASH = 0x0004, + + /* The following attrs are used for MDT interanl only, + * not visible to client */ + + /* Verify the dirent consistency */ + LUDA_VERIFY = 0x8000, + /* Only check but not repair the dirent inconsistency */ + LUDA_VERIFY_DRYRUN = 0x4000, + /* The dirent has been repaired, or to be repaired (dryrun). */ + LUDA_REPAIR = 0x2000, + /* The system is upgraded, has beed or to be repaired (dryrun). */ + LUDA_UPGRADE = 0x1000, + /* Ignore this record, go to next directly. */ + LUDA_IGNORE = 0x0800, }; +#define LU_DIRENT_ATTRS_MASK 0xf800 + /** * Layout of readdir pages, as transmitted on wire. */ @@ -854,7 +914,14 @@ struct lu_dirpage { }; enum lu_dirpage_flags { - LDF_EMPTY = 1 << 0 + /** + * dirpage contains no entry. + */ + LDF_EMPTY = 1 << 0, + /** + * last entry's lde_hash equals ldp_hash_end. + */ + LDF_COLLIDE = 1 << 1 }; static inline struct lu_dirent *lu_dirent_start(struct lu_dirpage *dp) @@ -900,7 +967,22 @@ static inline int lu_dirent_size(struct lu_dirent *ent) return le16_to_cpu(ent->lde_reclen); } -#define DIR_END_OFF 0xfffffffffffffffeULL +#define MDS_DIR_END_OFF 0xfffffffffffffffeULL + +/** + * MDS_READPAGE page size + * + * This is the directory page size packed in MDS_READPAGE RPC. + * It's different than CFS_PAGE_SIZE because the client needs to + * access the struct lu_dirpage header packed at the beginning of + * the "page" and without this there isn't any way to know find the + * lu_dirpage header is if client and server CFS_PAGE_SIZE differ. + */ +#define LU_PAGE_SHIFT 12 +#define LU_PAGE_SIZE (1UL << LU_PAGE_SHIFT) +#define LU_PAGE_MASK (~(LU_PAGE_SIZE - 1)) + +#define LU_PAGE_COUNT (1 << (CFS_PAGE_SHIFT - LU_PAGE_SHIFT)) /** @} lu_dir */ @@ -947,7 +1029,33 @@ struct lustre_msg_v2 { /* without gss, ptlrpc_body is put at the first buffer. */ #define PTLRPC_NUM_VERSIONS 4 -struct ptlrpc_body { +#define JOBSTATS_JOBID_SIZE 32 /* 32 bytes string */ +struct ptlrpc_body_v3 { + struct lustre_handle pb_handle; + __u32 pb_type; + __u32 pb_version; + __u32 pb_opc; + __u32 pb_status; + __u64 pb_last_xid; + __u64 pb_last_seen; + __u64 pb_last_committed; + __u64 pb_transno; + __u32 pb_flags; + __u32 pb_op_flags; + __u32 pb_conn_cnt; + __u32 pb_timeout; /* for req, the deadline, for rep, the service est */ + __u32 pb_service_time; /* for rep, actual service time */ + __u32 pb_limit; + __u64 pb_slv; + /* VBR: pre-versions */ + __u64 pb_pre_versions[PTLRPC_NUM_VERSIONS]; + /* padding for future needs */ + __u64 pb_padding[4]; + char pb_jobid[JOBSTATS_JOBID_SIZE]; +}; +#define ptlrpc_body ptlrpc_body_v3 + +struct ptlrpc_body_v2 { struct lustre_handle pb_handle; __u32 pb_type; __u32 pb_version; @@ -961,7 +1069,8 @@ struct ptlrpc_body { __u32 pb_op_flags; __u32 pb_conn_cnt; __u32 pb_timeout; /* for req, the deadline, for rep, the service est */ - __u32 pb_service_time; /* for rep, actual service time */ + __u32 pb_service_time; /* for rep, actual service time, also used for + net_latency of req */ __u32 pb_limit; __u64 pb_slv; /* VBR: pre-versions */ @@ -1051,7 +1160,7 @@ extern void lustre_swab_ptlrpc_body(struct ptlrpc_body *pb); #define OBD_CONNECT_RMT_CLIENT 0x10000ULL /*Remote client */ #define OBD_CONNECT_RMT_CLIENT_FORCE 0x20000ULL /*Remote client by force */ #define OBD_CONNECT_BRW_SIZE 0x40000ULL /*Max bytes per rpc */ -#define OBD_CONNECT_QUOTA64 0x80000ULL /*64bit qunit_data.qd_count */ +#define OBD_CONNECT_QUOTA64 0x80000ULL /*Not used since 2.4 */ #define OBD_CONNECT_MDS_CAPA 0x100000ULL /*MDS capability */ #define OBD_CONNECT_OSS_CAPA 0x200000ULL /*OSS capability */ #define OBD_CONNECT_CANCELSET 0x400000ULL /*Early batched cancels. */ @@ -1060,7 +1169,7 @@ extern void lustre_swab_ptlrpc_body(struct ptlrpc_body *pb); #define OBD_CONNECT_LRU_RESIZE 0x2000000ULL /*LRU resize feature. */ #define OBD_CONNECT_MDS_MDS 0x4000000ULL /*MDS-MDS connection */ #define OBD_CONNECT_REAL 0x8000000ULL /*real connection */ -#define OBD_CONNECT_CHANGE_QS 0x10000000ULL /*shrink/enlarge qunit */ +#define OBD_CONNECT_CHANGE_QS 0x10000000ULL /*Not used since 2.4 */ #define OBD_CONNECT_CKSUM 0x20000000ULL /*support several cksum algos*/ #define OBD_CONNECT_FID 0x40000000ULL /*FID is supported by server */ #define OBD_CONNECT_VBR 0x80000000ULL /*version based recovery */ @@ -1069,9 +1178,41 @@ extern void lustre_swab_ptlrpc_body(struct ptlrpc_body *pb); #define OBD_CONNECT_SKIP_ORPHAN 0x400000000ULL /* don't reuse orphan objids */ #define OBD_CONNECT_MAX_EASIZE 0x800000000ULL /* preserved for large EA */ #define OBD_CONNECT_FULL20 0x1000000000ULL /* it is 2.0 client */ -#define OBD_CONNECT_LAYOUTLOCK 0x2000000000ULL /* client supports layout lock */ -/* also update obd_connect_names[] for lprocfs_rd_connect_flags() - * and lustre/utils/wirecheck.c */ +#define OBD_CONNECT_LAYOUTLOCK 0x2000000000ULL /* client uses layout lock */ +#define OBD_CONNECT_64BITHASH 0x4000000000ULL /* client supports 64-bits + * directory hash */ +#define OBD_CONNECT_MAXBYTES 0x8000000000ULL /* max stripe size */ +#define OBD_CONNECT_IMP_RECOV 0x10000000000ULL /* imp recovery support */ +#define OBD_CONNECT_JOBSTATS 0x20000000000ULL /* jobid in ptlrpc_body */ +#define OBD_CONNECT_UMASK 0x40000000000ULL /* create uses client umask */ +#define OBD_CONNECT_EINPROGRESS 0x80000000000ULL /* client handles -EINPROGRESS + * RPC error properly */ +#define OBD_CONNECT_GRANT_PARAM 0x100000000000ULL/* extra grant params used for + * finer space reservation */ +#define OBD_CONNECT_FLOCK_OWNER 0x200000000000ULL /* for the fixed 1.8 + * policy and 2.x server */ +#define OBD_CONNECT_LVB_TYPE 0x400000000000ULL /* variable type of LVB */ +#define OBD_CONNECT_NANOSEC_TIME 0x800000000000ULL /* nanosecond timestamps */ +#define OBD_CONNECT_LIGHTWEIGHT 0x1000000000000ULL/* lightweight connection */ +#define OBD_CONNECT_SHORTIO 0x2000000000000ULL/* short io */ +#define OBD_CONNECT_PINGLESS 0x4000000000000ULL/* pings not required */ +/* XXX README XXX: + * Please DO NOT add flag values here before first ensuring that this same + * flag value is not in use on some other branch. Please clear any such + * changes with senior engineers before starting to use a new flag. Then, + * submit a small patch against EVERY branch that ONLY adds the new flag + * and updates obd_connect_names[] for lprocfs_rd_connect_flags(), so it + * can be approved and landed easily to reserve the flag for future use. */ + +/* The MNE_SWAB flag is overloading the MDS_MDS bit only for the MGS + * connection. It is a temporary bug fix for Imperative Recovery interop + * between 2.2 and 2.3 x86/ppc nodes, and can be removed when interop for + * 2.2 clients/servers is no longer needed. LU-1252/LU-1644. */ +#define OBD_CONNECT_MNE_SWAB OBD_CONNECT_MDS_MDS + +#define OCD_HAS_FLAG(ocd, flg) \ + (!!((ocd)->ocd_connect_flags & OBD_CONNECT_##flg)) + #ifdef HAVE_LRU_RESIZE_SUPPORT #define LRU_RESIZE_CONNECT_FLAG OBD_CONNECT_LRU_RESIZE @@ -1081,30 +1222,46 @@ extern void lustre_swab_ptlrpc_body(struct ptlrpc_body *pb); #define MDT_CONNECT_SUPPORTED (OBD_CONNECT_RDONLY | OBD_CONNECT_VERSION | \ OBD_CONNECT_ACL | OBD_CONNECT_XATTR | \ - OBD_CONNECT_IBITS | OBD_CONNECT_JOIN | \ + OBD_CONNECT_IBITS | \ OBD_CONNECT_NODEVOH | OBD_CONNECT_ATTRFID | \ OBD_CONNECT_CANCELSET | OBD_CONNECT_AT | \ OBD_CONNECT_RMT_CLIENT | \ OBD_CONNECT_RMT_CLIENT_FORCE | \ - OBD_CONNECT_MDS_CAPA | OBD_CONNECT_OSS_CAPA | \ - OBD_CONNECT_MDS_MDS | OBD_CONNECT_FID | \ - LRU_RESIZE_CONNECT_FLAG | OBD_CONNECT_VBR | \ - OBD_CONNECT_LOV_V3 | OBD_CONNECT_SOM | \ - OBD_CONNECT_FULL20) + OBD_CONNECT_BRW_SIZE | OBD_CONNECT_MDS_CAPA | \ + OBD_CONNECT_OSS_CAPA | OBD_CONNECT_MDS_MDS | \ + OBD_CONNECT_FID | LRU_RESIZE_CONNECT_FLAG | \ + OBD_CONNECT_VBR | OBD_CONNECT_LOV_V3 | \ + OBD_CONNECT_SOM | OBD_CONNECT_FULL20 | \ + OBD_CONNECT_64BITHASH | OBD_CONNECT_JOBSTATS | \ + OBD_CONNECT_EINPROGRESS | \ + OBD_CONNECT_LIGHTWEIGHT | OBD_CONNECT_UMASK | \ + OBD_CONNECT_LVB_TYPE | OBD_CONNECT_LAYOUTLOCK |\ + OBD_CONNECT_PINGLESS) #define OST_CONNECT_SUPPORTED (OBD_CONNECT_SRVLOCK | OBD_CONNECT_GRANT | \ OBD_CONNECT_REQPORTAL | OBD_CONNECT_VERSION | \ OBD_CONNECT_TRUNCLOCK | OBD_CONNECT_INDEX | \ - OBD_CONNECT_BRW_SIZE | OBD_CONNECT_QUOTA64 | \ + OBD_CONNECT_BRW_SIZE | OBD_CONNECT_OSS_CAPA | \ OBD_CONNECT_CANCELSET | OBD_CONNECT_AT | \ LRU_RESIZE_CONNECT_FLAG | OBD_CONNECT_CKSUM | \ - OBD_CONNECT_CHANGE_QS | \ - OBD_CONNECT_OSS_CAPA | OBD_CONNECT_RMT_CLIENT | \ + OBD_CONNECT_RMT_CLIENT | \ OBD_CONNECT_RMT_CLIENT_FORCE | OBD_CONNECT_VBR | \ OBD_CONNECT_MDS | OBD_CONNECT_SKIP_ORPHAN | \ - OBD_CONNECT_GRANT_SHRINK | OBD_CONNECT_FULL20) + OBD_CONNECT_GRANT_SHRINK | OBD_CONNECT_FULL20 | \ + OBD_CONNECT_64BITHASH | OBD_CONNECT_MAXBYTES | \ + OBD_CONNECT_MAX_EASIZE | \ + OBD_CONNECT_EINPROGRESS | \ + OBD_CONNECT_JOBSTATS | \ + OBD_CONNECT_LIGHTWEIGHT | OBD_CONNECT_LVB_TYPE|\ + OBD_CONNECT_LAYOUTLOCK | OBD_CONNECT_FID | \ + OBD_CONNECT_PINGLESS) #define ECHO_CONNECT_SUPPORTED (0) #define MGS_CONNECT_SUPPORTED (OBD_CONNECT_VERSION | OBD_CONNECT_AT | \ - OBD_CONNECT_FULL20) + OBD_CONNECT_FULL20 | OBD_CONNECT_IMP_RECOV | \ + OBD_CONNECT_MNE_SWAB | OBD_CONNECT_PINGLESS) + +/* Features required for this version of the client to work with server */ +#define CLIENT_CONNECT_MDT_REQD (OBD_CONNECT_IBITS | OBD_CONNECT_FID | \ + OBD_CONNECT_FULL20) #define OBD_OCD_VERSION(major,minor,patch,fix) (((major)<<24) + ((minor)<<16) +\ ((patch)<<8) + (fix)) @@ -1117,22 +1274,71 @@ extern void lustre_swab_ptlrpc_body(struct ptlrpc_body *pb); * * If we eventually have separate connect data for different types, which we * almost certainly will, then perhaps we stick a union in here. */ -struct obd_connect_data { +struct obd_connect_data_v1 { __u64 ocd_connect_flags; /* OBD_CONNECT_* per above */ __u32 ocd_version; /* lustre release version number */ __u32 ocd_grant; /* initial cache grant amount (bytes) */ __u32 ocd_index; /* LOV index to connect to */ __u32 ocd_brw_size; /* Maximum BRW size in bytes */ __u64 ocd_ibits_known; /* inode bits this client understands */ - __u32 ocd_nllu; /* non-local-lustre-user */ - __u32 ocd_nllg; /* non-local-lustre-group */ + __u8 ocd_blocksize; /* log2 of the backend filesystem blocksize */ + __u8 ocd_inodespace; /* log2 of the per-inode space consumption */ + __u16 ocd_grant_extent; /* per-extent grant overhead, in 1K blocks */ + __u32 ocd_unused; /* also fix lustre_swab_connect */ __u64 ocd_transno; /* first transno from client to be replayed */ __u32 ocd_group; /* MDS group on OST */ __u32 ocd_cksum_types; /* supported checksum algorithms */ - __u64 padding1; /* also fix lustre_swab_connect */ - __u64 padding2; /* also fix lustre_swab_connect */ + __u32 ocd_max_easize; /* How big LOV EA can be on MDS */ + __u32 ocd_instance; /* also fix lustre_swab_connect */ + __u64 ocd_maxbytes; /* Maximum stripe size in bytes */ }; +struct obd_connect_data { + __u64 ocd_connect_flags; /* OBD_CONNECT_* per above */ + __u32 ocd_version; /* lustre release version number */ + __u32 ocd_grant; /* initial cache grant amount (bytes) */ + __u32 ocd_index; /* LOV index to connect to */ + __u32 ocd_brw_size; /* Maximum BRW size in bytes */ + __u64 ocd_ibits_known; /* inode bits this client understands */ + __u8 ocd_blocksize; /* log2 of the backend filesystem blocksize */ + __u8 ocd_inodespace; /* log2 of the per-inode space consumption */ + __u16 ocd_grant_extent; /* per-extent grant overhead, in 1K blocks */ + __u32 ocd_unused; /* also fix lustre_swab_connect */ + __u64 ocd_transno; /* first transno from client to be replayed */ + __u32 ocd_group; /* MDS group on OST */ + __u32 ocd_cksum_types; /* supported checksum algorithms */ + __u32 ocd_max_easize; /* How big LOV EA can be on MDS */ + __u32 ocd_instance; /* instance # of this target */ + __u64 ocd_maxbytes; /* Maximum stripe size in bytes */ + /* Fields after ocd_maxbytes are only accessible by the receiver + * if the corresponding flag in ocd_connect_flags is set. Accessing + * any field after ocd_maxbytes on the receiver without a valid flag + * may result in out-of-bound memory access and kernel oops. */ + __u64 padding1; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding2; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding3; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding4; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding5; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding6; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding7; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding8; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 padding9; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 paddingA; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 paddingB; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 paddingC; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 paddingD; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 paddingE; /* added 2.1.0. also fix lustre_swab_connect */ + __u64 paddingF; /* added 2.1.0. also fix lustre_swab_connect */ +}; +/* XXX README XXX: + * Please DO NOT use any fields here before first ensuring that this same + * field is not in use on some other branch. Please clear any such changes + * with senior engineers before starting to use a new field. Then, submit + * a small patch against EVERY branch that ONLY adds the new field along with + * the matching OBD_CONNECT flag, so that can be approved and landed easily to + * reserve the flag for future use. */ + + extern void lustre_swab_connect(struct obd_connect_data *ocd); /* @@ -1144,6 +1350,7 @@ extern void lustre_swab_connect(struct obd_connect_data *ocd); typedef enum { OBD_CKSUM_CRC32 = 0x00000001, OBD_CKSUM_ADLER = 0x00000002, + OBD_CKSUM_CRC32C= 0x00000004, } cksum_type_t; /* @@ -1170,7 +1377,7 @@ typedef enum { OST_SET_INFO = 17, OST_QUOTACHECK = 18, OST_QUOTACTL = 19, - OST_QUOTA_ADJUST_QUNIT = 20, + OST_QUOTA_ADJUST_QUNIT = 20, /* not used since 2.4 */ OST_LAST_OPC } ost_cmd_t; #define OST_FIRST_OPC OST_REPLY @@ -1189,14 +1396,20 @@ enum obdo_flags { OBD_FL_SRVLOCK = 0x00000800, /* delegate DLM locking to server */ OBD_FL_CKSUM_CRC32 = 0x00001000, /* CRC32 checksum type */ OBD_FL_CKSUM_ADLER = 0x00002000, /* ADLER checksum type */ - OBD_FL_CKSUM_RSVD1 = 0x00004000, /* for future cksum types */ + OBD_FL_CKSUM_CRC32C = 0x00004000, /* CRC32C checksum type */ OBD_FL_CKSUM_RSVD2 = 0x00008000, /* for future cksum types */ OBD_FL_CKSUM_RSVD3 = 0x00010000, /* for future cksum types */ OBD_FL_SHRINK_GRANT = 0x00020000, /* object shrink the grant */ - OBD_FL_MMAP = 0x00040000, /* object is mmapped on the client */ + OBD_FL_MMAP = 0x00040000, /* object is mmapped on the client. + * XXX: obsoleted - reserved for old + * clients prior than 2.2 */ OBD_FL_RECOV_RESEND = 0x00080000, /* recoverable resent */ + OBD_FL_NOSPC_BLK = 0x00100000, /* no more block space on OST */ - OBD_FL_CKSUM_ALL = OBD_FL_CKSUM_CRC32 | OBD_FL_CKSUM_ADLER, + /* Note that while these checksum values are currently separate bits, + * in 2.x we can actually allow all values from 1-31 if we wanted. */ + OBD_FL_CKSUM_ALL = OBD_FL_CKSUM_CRC32 | OBD_FL_CKSUM_ADLER | + OBD_FL_CKSUM_CRC32C, /* mask for local-only flag, which won't be sent over network */ OBD_FL_LOCAL_MASK = 0xF0000000, @@ -1207,14 +1420,26 @@ enum obdo_flags { #define LOV_MAGIC_JOIN_V1 0x0BD20BD0 #define LOV_MAGIC_V3 0x0BD30BD0 +/* + * magic for fully defined striping + * the idea is that we should have different magics for striping "hints" + * (struct lov_user_md_v[13]) and defined ready-to-use striping (struct + * lov_mds_md_v[13]). at the moment the magics are used in wire protocol, + * we can't just change it w/o long way preparation, but we still need a + * mechanism to allow LOD to differentiate hint versus ready striping. + * so, at the moment we do a trick: MDT knows what to expect from request + * depending on the case (replay uses ready striping, non-replay req uses + * hints), so MDT replaces magic with appropriate one and now LOD can + * easily understand what's inside -bzzz + */ +#define LOV_MAGIC_V1_DEF 0x0CD10BD0 +#define LOV_MAGIC_V3_DEF 0x0CD30BD0 + #define LOV_PATTERN_RAID0 0x001 /* stripes are used round-robin */ #define LOV_PATTERN_RAID1 0x002 /* stripes are mirrors of each other */ #define LOV_PATTERN_FIRST 0x100 /* first stripe is not in round-robin */ #define LOV_PATTERN_CMOBD 0x200 -#define LOV_OBJECT_GROUP_DEFAULT ~0ULL -#define LOV_OBJECT_GROUP_CLEAR 0ULL - #define lov_ost_data lov_ost_data_v1 struct lov_ost_data_v1 { /* per-stripe data structure (little-endian)*/ __u64 l_object_id; /* OST object ID */ @@ -1230,7 +1455,9 @@ struct lov_mds_md_v1 { /* LOV EA mds/wire data (little-endian) */ __u64 lmm_object_id; /* LOV object ID */ __u64 lmm_object_seq; /* LOV object seq number */ __u32 lmm_stripe_size; /* size of stripe in bytes */ - __u32 lmm_stripe_count; /* num stripes in use for this object */ + /* lmm_stripe_count used to be __u32 */ + __u16 lmm_stripe_count; /* num stripes in use for this object */ + __u16 lmm_layout_gen; /* layout generation number */ struct lov_ost_data_v1 lmm_objects[0]; /* per-stripe data */ }; @@ -1250,6 +1477,10 @@ struct lov_mds_md_v1 { /* LOV EA mds/wire data (little-endian) */ #define XATTR_NAME_LMA "trusted.lma" #define XATTR_NAME_LMV "trusted.lmv" #define XATTR_NAME_LINK "trusted.link" +#define XATTR_NAME_FID "trusted.fid" +#define XATTR_NAME_VERSION "trusted.version" +#define XATTR_NAME_SOM "trusted.som" +#define XATTR_NAME_HSM "trusted.hsm" struct lov_mds_md_v3 { /* LOV EA mds/wire data (little-endian) */ @@ -1258,7 +1489,9 @@ struct lov_mds_md_v3 { /* LOV EA mds/wire data (little-endian) */ __u64 lmm_object_id; /* LOV object ID */ __u64 lmm_object_seq; /* LOV object seq number */ __u32 lmm_stripe_size; /* size of stripe in bytes */ - __u32 lmm_stripe_count; /* num stripes in use for this object */ + /* lmm_stripe_count used to be __u32 */ + __u16 lmm_stripe_count; /* num stripes in use for this object */ + __u16 lmm_layout_gen; /* layout generation number */ char lmm_pool_name[LOV_MAXPOOLNAME]; /* must be 32bit aligned */ struct lov_ost_data_v1 lmm_objects[0]; /* per-stripe data */ }; @@ -1300,25 +1533,30 @@ struct lov_mds_md_v3 { /* LOV EA mds/wire data (little-endian) */ #define OBD_MD_MDS (0x0000000100000000ULL) /* where an inode lives on */ #define OBD_MD_REINT (0x0000000200000000ULL) /* reintegrate oa */ #define OBD_MD_MEA (0x0000000400000000ULL) /* CMD split EA */ -#define OBD_MD_MDTIDX (0x0000000800000000ULL) /* Get MDT index */ - -#define OBD_MD_FLXATTR (0x0000001000000000ULL) /* xattr */ -#define OBD_MD_FLXATTRLS (0x0000002000000000ULL) /* xattr list */ -#define OBD_MD_FLXATTRRM (0x0000004000000000ULL) /* xattr remove */ -#define OBD_MD_FLACL (0x0000008000000000ULL) /* ACL */ -#define OBD_MD_FLRMTPERM (0x0000010000000000ULL) /* remote permission */ -#define OBD_MD_FLMDSCAPA (0x0000020000000000ULL) /* MDS capability */ -#define OBD_MD_FLOSSCAPA (0x0000040000000000ULL) /* OSS capability */ -#define OBD_MD_FLCKSPLIT (0x0000080000000000ULL) /* Check split on server */ -#define OBD_MD_FLCROSSREF (0x0000100000000000ULL) /* Cross-ref case */ + +/* OBD_MD_MDTIDX is used to get MDT index, but it is never been used overwire, + * and it is already obsolete since 2.3 */ +/* #define OBD_MD_MDTIDX (0x0000000800000000ULL) */ + +#define OBD_MD_FLXATTR (0x0000001000000000ULL) /* xattr */ +#define OBD_MD_FLXATTRLS (0x0000002000000000ULL) /* xattr list */ +#define OBD_MD_FLXATTRRM (0x0000004000000000ULL) /* xattr remove */ +#define OBD_MD_FLACL (0x0000008000000000ULL) /* ACL */ +#define OBD_MD_FLRMTPERM (0x0000010000000000ULL) /* remote permission */ +#define OBD_MD_FLMDSCAPA (0x0000020000000000ULL) /* MDS capability */ +#define OBD_MD_FLOSSCAPA (0x0000040000000000ULL) /* OSS capability */ +#define OBD_MD_FLCKSPLIT (0x0000080000000000ULL) /* Check split on server */ +#define OBD_MD_FLCROSSREF (0x0000100000000000ULL) /* Cross-ref case */ #define OBD_MD_FLGETATTRLOCK (0x0000200000000000ULL) /* Get IOEpoch attributes * under lock */ -#define OBD_FL_TRUNC (0x0000200000000000ULL) /* for filter_truncate */ +#define OBD_MD_FLOBJCOUNT (0x0000400000000000ULL) /* for multiple destroy */ + +#define OBD_MD_FLRMTLSETFACL (0x0001000000000000ULL) /* lfs lsetfacl case */ +#define OBD_MD_FLRMTLGETFACL (0x0002000000000000ULL) /* lfs lgetfacl case */ +#define OBD_MD_FLRMTRSETFACL (0x0004000000000000ULL) /* lfs rsetfacl case */ +#define OBD_MD_FLRMTRGETFACL (0x0008000000000000ULL) /* lfs rgetfacl case */ -#define OBD_MD_FLRMTLSETFACL (0x0001000000000000ULL) /* lfs lsetfacl case */ -#define OBD_MD_FLRMTLGETFACL (0x0002000000000000ULL) /* lfs lgetfacl case */ -#define OBD_MD_FLRMTRSETFACL (0x0004000000000000ULL) /* lfs rsetfacl case */ -#define OBD_MD_FLRMTRGETFACL (0x0008000000000000ULL) /* lfs rgetfacl case */ +#define OBD_MD_FLDATAVERSION (0x0010000000000000ULL) /* iversion sum */ #define OBD_MD_FLGETATTR (OBD_MD_FLID | OBD_MD_FLATIME | OBD_MD_FLMTIME | \ OBD_MD_FLCTIME | OBD_MD_FLSIZE | OBD_MD_FLBLKSZ | \ @@ -1329,18 +1567,23 @@ struct lov_mds_md_v3 { /* LOV EA mds/wire data (little-endian) */ /* don't forget obdo_fid which is way down at the bottom so it can * come after the definition of llog_cookie */ +enum hss_valid { + HSS_SETMASK = 0x01, + HSS_CLEARMASK = 0x02, + HSS_ARCHIVE_ID = 0x04, +}; + +struct hsm_state_set { + __u32 hss_valid; + __u32 hss_archive_id; + __u64 hss_setmask; + __u64 hss_clearmask; +}; + +extern void lustre_swab_hsm_user_state(struct hsm_user_state *hus); +extern void lustre_swab_hsm_state_set(struct hsm_state_set *hss); extern void lustre_swab_obd_statfs (struct obd_statfs *os); -#define OBD_STATFS_NODELAY 0x0001 /* requests should be send without delay - * and resends for avoid deadlocks */ -#define OBD_STATFS_FROM_CACHE 0x0002 /* the statfs callback should not update - * obd_osfs_age */ -#define OBD_STATFS_PTLRPCD 0x0004 /* requests will be sent via ptlrpcd - * instead of a specific set. This - * means that we cannot rely on the set - * interpret routine to be called. - * lov_statfs_fini() must thus be called - * by the request interpret routine */ /* ost_body.data values for OST_BRW */ @@ -1358,6 +1601,8 @@ extern void lustre_swab_obd_statfs (struct obd_statfs *os); #define OBD_BRW_SRVLOCK 0x200 /* Client holds no lock over this page */ #define OBD_BRW_ASYNC 0x400 /* Server may delay commit to disk */ #define OBD_BRW_MEMALLOC 0x800 /* Client runs in the "kswapd" context */ +#define OBD_BRW_OVER_USRQUOTA 0x1000 /* Running out of user quota */ +#define OBD_BRW_OVER_GRPQUOTA 0x2000 /* Running out of group quota */ #define OBD_OBJECT_EOF 0xffffffffffffffffULL @@ -1365,12 +1610,14 @@ extern void lustre_swab_obd_statfs (struct obd_statfs *os); #define OST_MAX_PRECREATE 20000 struct obd_ioobj { - obd_id ioo_id; - obd_seq ioo_seq; - __u32 ioo_type; - __u32 ioo_bufcnt; + struct ost_id ioo_oid; + __u32 ioo_type; + __u32 ioo_bufcnt; }; +#define ioo_id ioo_oid.oi_id +#define ioo_seq ioo_oid.oi_seq + extern void lustre_swab_obd_ioobj (struct obd_ioobj *ioo); /* multiple of 8 bytes => can array */ @@ -1394,15 +1641,208 @@ extern void lustre_swab_niobuf_remote (struct niobuf_remote *nbr); do { blocks = OST_LVB_ERR_INIT + rc; } while (0) #define OST_LVB_GET_ERR(blocks) (int)(blocks - OST_LVB_ERR_INIT) +struct ost_lvb_v1 { + __u64 lvb_size; + obd_time lvb_mtime; + obd_time lvb_atime; + obd_time lvb_ctime; + __u64 lvb_blocks; +}; + +extern void lustre_swab_ost_lvb_v1(struct ost_lvb_v1 *lvb); + struct ost_lvb { - __u64 lvb_size; - obd_time lvb_mtime; - obd_time lvb_atime; - obd_time lvb_ctime; - __u64 lvb_blocks; + __u64 lvb_size; + obd_time lvb_mtime; + obd_time lvb_atime; + obd_time lvb_ctime; + __u64 lvb_blocks; + __u32 lvb_mtime_ns; + __u32 lvb_atime_ns; + __u32 lvb_ctime_ns; + __u32 lvb_padding; +}; + +extern void lustre_swab_ost_lvb(struct ost_lvb *lvb); + +/* + * lquota data structures + */ + +#ifndef QUOTABLOCK_BITS +#define QUOTABLOCK_BITS 10 +#endif + +#ifndef QUOTABLOCK_SIZE +#define QUOTABLOCK_SIZE (1 << QUOTABLOCK_BITS) +#endif + +#ifndef toqb +#define toqb(x) (((x) + QUOTABLOCK_SIZE - 1) >> QUOTABLOCK_BITS) +#endif + +/* The lquota_id structure is an union of all the possible identifier types that + * can be used with quota, this includes: + * - 64-bit user ID + * - 64-bit group ID + * - a FID which can be used for per-directory quota in the future */ +union lquota_id { + struct lu_fid qid_fid; /* FID for per-directory quota */ + __u64 qid_uid; /* user identifier */ + __u64 qid_gid; /* group identifier */ +}; + +/* quotactl management */ +struct obd_quotactl { + __u32 qc_cmd; + __u32 qc_type; /* see Q_* flag below */ + __u32 qc_id; + __u32 qc_stat; + struct obd_dqinfo qc_dqinfo; + struct obd_dqblk qc_dqblk; +}; + +extern void lustre_swab_obd_quotactl(struct obd_quotactl *q); + +#define Q_QUOTACHECK 0x800100 /* deprecated as of 2.4 */ +#define Q_INITQUOTA 0x800101 /* deprecated as of 2.4 */ +#define Q_GETOINFO 0x800102 /* get obd quota info */ +#define Q_GETOQUOTA 0x800103 /* get obd quotas */ +#define Q_FINVALIDATE 0x800104 /* deprecated as of 2.4 */ + +#define Q_COPY(out, in, member) (out)->member = (in)->member + +#define QCTL_COPY(out, in) \ +do { \ + Q_COPY(out, in, qc_cmd); \ + Q_COPY(out, in, qc_type); \ + Q_COPY(out, in, qc_id); \ + Q_COPY(out, in, qc_stat); \ + Q_COPY(out, in, qc_dqinfo); \ + Q_COPY(out, in, qc_dqblk); \ +} while (0) + +/* Body of quota request used for quota acquire/release RPCs between quota + * master (aka QMT) and slaves (ak QSD). */ +struct quota_body { + struct lu_fid qb_fid; /* FID of global index packing the pool ID + * and type (data or metadata) as well as + * the quota type (user or group). */ + union lquota_id qb_id; /* uid or gid or directory FID */ + __u32 qb_flags; /* see below */ + __u32 qb_padding; + __u64 qb_count; /* acquire/release count (kbytes/inodes) */ + __u64 qb_usage; /* current slave usage (kbytes/inodes) */ + __u64 qb_slv_ver; /* slave index file version */ + struct lustre_handle qb_lockh; /* per-ID lock handle */ + struct lustre_handle qb_glb_lockh; /* global lock handle */ + __u64 qb_padding1[4]; +}; + +/* When the quota_body is used in the reply of quota global intent + * lock (IT_QUOTA_CONN) reply, qb_fid contains slave index file FID. */ +#define qb_slv_fid qb_fid +/* qb_usage is the current qunit (in kbytes/inodes) when quota_body is used in + * quota reply */ +#define qb_qunit qb_usage + +#define QUOTA_DQACQ_FL_ACQ 0x1 /* acquire quota */ +#define QUOTA_DQACQ_FL_PREACQ 0x2 /* pre-acquire */ +#define QUOTA_DQACQ_FL_REL 0x4 /* release quota */ +#define QUOTA_DQACQ_FL_REPORT 0x8 /* report usage */ + +extern void lustre_swab_quota_body(struct quota_body *b); + +/* Quota types currently supported */ +enum { + LQUOTA_TYPE_USR = 0x00, /* maps to USRQUOTA */ + LQUOTA_TYPE_GRP = 0x01, /* maps to GRPQUOTA */ + LQUOTA_TYPE_MAX +}; + +/* There are 2 different resource types on which a quota limit can be enforced: + * - inodes on the MDTs + * - blocks on the OSTs */ +enum { + LQUOTA_RES_MD = 0x01, /* skip 0 to avoid null oid in FID */ + LQUOTA_RES_DT = 0x02, + LQUOTA_LAST_RES, + LQUOTA_FIRST_RES = LQUOTA_RES_MD +}; +#define LQUOTA_NR_RES (LQUOTA_LAST_RES - LQUOTA_FIRST_RES + 1) + +/* + * Space accounting support + * Format of an accounting record, providing disk usage information for a given + * user or group + */ +struct lquota_acct_rec { /* 16 bytes */ + __u64 bspace; /* current space in use */ + __u64 ispace; /* current # inodes in use */ +}; + +/* + * Global quota index support + * Format of a global record, providing global quota settings for a given quota + * identifier + */ +struct lquota_glb_rec { /* 32 bytes */ + __u64 qbr_hardlimit; /* quota hard limit, in #inodes or kbytes */ + __u64 qbr_softlimit; /* quota soft limit, in #inodes or kbytes */ + __u64 qbr_time; /* grace time, in seconds */ + __u64 qbr_granted; /* how much is granted to slaves, in #inodes or + * kbytes */ +}; + +/* + * Slave index support + * Format of a slave record, recording how much space is granted to a given + * slave + */ +struct lquota_slv_rec { /* 8 bytes */ + __u64 qsr_granted; /* space granted to the slave for the key=ID, + * in #inodes or kbytes */ +}; + +/* Data structures associated with the quota locks */ + +/* Glimpse descriptor used for the index & per-ID quota locks */ +struct ldlm_gl_lquota_desc { + union lquota_id gl_id; /* quota ID subject to the glimpse */ + __u64 gl_flags; /* see LQUOTA_FL* below */ + __u64 gl_ver; /* new index version */ + __u64 gl_hardlimit; /* new hardlimit or qunit value */ + __u64 gl_softlimit; /* new softlimit */ + __u64 gl_time; + __u64 gl_pad2; +}; +#define gl_qunit gl_hardlimit /* current qunit value used when + * glimpsing per-ID quota locks */ + +/* quota glimpse flags */ +#define LQUOTA_FL_EDQUOT 0x1 /* user/group out of quota space on QMT */ + +/* LVB used with quota (global and per-ID) locks */ +struct lquota_lvb { + __u64 lvb_flags; /* see LQUOTA_FL* above */ + __u64 lvb_id_may_rel; /* space that might be released later */ + __u64 lvb_id_rel; /* space released by the slave for this ID */ + __u64 lvb_id_qunit; /* current qunit value */ + __u64 lvb_pad1; }; -extern void lustre_swab_ost_lvb(struct ost_lvb *); +extern void lustre_swab_lquota_lvb(struct lquota_lvb *lvb); + +/* LVB used with global quota lock */ +#define lvb_glb_ver lvb_id_may_rel /* current version of the global index */ + +/* op codes */ +typedef enum { + QUOTA_DQACQ = 601, + QUOTA_DQREL = 602, + QUOTA_LAST_OPC +} quota_cmd_t; +#define QUOTA_FIRST_OPC QUOTA_DQACQ /* * MDS REQ RECORDS @@ -1410,45 +1850,61 @@ extern void lustre_swab_ost_lvb(struct ost_lvb *); /* opcodes */ typedef enum { - MDS_GETATTR = 33, - MDS_GETATTR_NAME = 34, - MDS_CLOSE = 35, - MDS_REINT = 36, - MDS_READPAGE = 37, - MDS_CONNECT = 38, - MDS_DISCONNECT = 39, - MDS_GETSTATUS = 40, - MDS_STATFS = 41, - MDS_PIN = 42, - MDS_UNPIN = 43, - MDS_SYNC = 44, - MDS_DONE_WRITING = 45, - MDS_SET_INFO = 46, - MDS_QUOTACHECK = 47, - MDS_QUOTACTL = 48, - MDS_GETXATTR = 49, - MDS_SETXATTR = 50, /* obsolete, now it's MDS_REINT op */ - MDS_WRITEPAGE = 51, - MDS_IS_SUBDIR = 52, - MDS_GET_INFO = 53, - MDS_LAST_OPC + MDS_GETATTR = 33, + MDS_GETATTR_NAME = 34, + MDS_CLOSE = 35, + MDS_REINT = 36, + MDS_READPAGE = 37, + MDS_CONNECT = 38, + MDS_DISCONNECT = 39, + MDS_GETSTATUS = 40, + MDS_STATFS = 41, + MDS_PIN = 42, + MDS_UNPIN = 43, + MDS_SYNC = 44, + MDS_DONE_WRITING = 45, + MDS_SET_INFO = 46, + MDS_QUOTACHECK = 47, + MDS_QUOTACTL = 48, + MDS_GETXATTR = 49, + MDS_SETXATTR = 50, /* obsolete, now it's MDS_REINT op */ + MDS_WRITEPAGE = 51, + MDS_IS_SUBDIR = 52, + MDS_GET_INFO = 53, + MDS_HSM_STATE_GET = 54, + MDS_HSM_STATE_SET = 55, + MDS_HSM_ACTION = 56, + MDS_HSM_PROGRESS = 57, + MDS_HSM_REQUEST = 58, + MDS_HSM_CT_REGISTER = 59, + MDS_HSM_CT_UNREGISTER = 60, + MDS_LAST_OPC } mds_cmd_t; #define MDS_FIRST_OPC MDS_GETATTR + +/* opcodes for object update */ +typedef enum { + UPDATE_OBJ = 1000, + UPDATE_LAST_OPC +} update_cmd_t; + +#define UPDATE_FIRST_OPC UPDATE_OBJ + /* * Do not exceed 63 */ typedef enum { - REINT_SETATTR = 1, - REINT_CREATE = 2, - REINT_LINK = 3, - REINT_UNLINK = 4, - REINT_RENAME = 5, - REINT_OPEN = 6, - REINT_SETXATTR = 7, -// REINT_CLOSE = 8, + REINT_SETATTR = 1, + REINT_CREATE = 2, + REINT_LINK = 3, + REINT_UNLINK = 4, + REINT_RENAME = 5, + REINT_OPEN = 6, + REINT_SETXATTR = 7, + REINT_RMENTRY = 8, // REINT_WRITE = 9, REINT_MAX } mds_reint_t, mdt_reint_t; @@ -1471,125 +1927,90 @@ extern void lustre_swab_generic_32s (__u32 *val); #define MDS_INODELOCK_LOOKUP 0x000001 /* dentry, mode, owner, group */ #define MDS_INODELOCK_UPDATE 0x000002 /* size, links, timestamps */ #define MDS_INODELOCK_OPEN 0x000004 /* For opened files */ +#define MDS_INODELOCK_LAYOUT 0x000008 /* for layout */ +#define MDS_INODELOCK_PERM 0x000010 /* for permission */ -/* Do not forget to increase MDS_INODELOCK_MAXSHIFT when adding new bits */ -#define MDS_INODELOCK_MAXSHIFT 2 +#define MDS_INODELOCK_MAXSHIFT 4 /* This FULL lock is useful to take on unlink sort of operations */ #define MDS_INODELOCK_FULL ((1<<(MDS_INODELOCK_MAXSHIFT+1))-1) extern void lustre_swab_ll_fid (struct ll_fid *fid); -#define MDS_STATUS_CONN 1 -#define MDS_STATUS_LOV 2 - -struct mds_status_req { - __u32 flags; - __u32 repbuf; +/* NOTE: until Lustre 1.8.7/2.1.1 the fid_ver() was packed into name[2], + * but was moved into name[1] along with the OID to avoid consuming the + * name[2,3] fields that need to be used for the quota id (also a FID). */ +enum { + LUSTRE_RES_ID_SEQ_OFF = 0, + LUSTRE_RES_ID_VER_OID_OFF = 1, + LUSTRE_RES_ID_WAS_VER_OFF = 2, /* see note above */ + LUSTRE_RES_ID_QUOTA_SEQ_OFF = 2, + LUSTRE_RES_ID_QUOTA_VER_OID_OFF = 3, + LUSTRE_RES_ID_HSH_OFF = 3 }; -extern void lustre_swab_mds_status_req (struct mds_status_req *r); +#define MDS_STATUS_CONN 1 +#define MDS_STATUS_LOV 2 /* mdt_thread_info.mti_flags. */ enum md_op_flags { - /* The flag indicates Size-on-MDS attributes are changed. */ - MF_SOM_CHANGE = (1 << 0), - /* Flags indicates an epoch opens or closes. */ - MF_EPOCH_OPEN = (1 << 1), - MF_EPOCH_CLOSE = (1 << 2), - MF_MDC_CANCEL_FID1 = (1 << 3), - MF_MDC_CANCEL_FID2 = (1 << 4), - MF_MDC_CANCEL_FID3 = (1 << 5), - MF_MDC_CANCEL_FID4 = (1 << 6), - /* There is a pending attribute update. */ - MF_SOM_AU = (1 << 7), - /* Cancel OST locks while getattr OST attributes. */ - MF_GETATTR_LOCK = (1 << 8), + /* The flag indicates Size-on-MDS attributes are changed. */ + MF_SOM_CHANGE = (1 << 0), + /* Flags indicates an epoch opens or closes. */ + MF_EPOCH_OPEN = (1 << 1), + MF_EPOCH_CLOSE = (1 << 2), + MF_MDC_CANCEL_FID1 = (1 << 3), + MF_MDC_CANCEL_FID2 = (1 << 4), + MF_MDC_CANCEL_FID3 = (1 << 5), + MF_MDC_CANCEL_FID4 = (1 << 6), + /* There is a pending attribute update. */ + MF_SOM_AU = (1 << 7), + /* Cancel OST locks while getattr OST attributes. */ + MF_GETATTR_LOCK = (1 << 8), + MF_GET_MDT_IDX = (1 << 9), }; #define MF_SOM_LOCAL_FLAGS (MF_SOM_CHANGE | MF_EPOCH_OPEN | MF_EPOCH_CLOSE) -#define MDS_BFLAG_UNCOMMITTED_WRITES 0x1 +#define LUSTRE_BFLAG_UNCOMMITTED_WRITES 0x1 -/* these should be identical to their EXT3_*_FL counterparts, and are - * redefined here only to avoid dragging in ext3_fs.h */ -#define MDS_SYNC_FL 0x00000008 /* Synchronous updates */ -#define MDS_IMMUTABLE_FL 0x00000010 /* Immutable file */ -#define MDS_APPEND_FL 0x00000020 /* writes to file may only append */ -#define MDS_NOATIME_FL 0x00000080 /* do not update atime */ -#define MDS_DIRSYNC_FL 0x00010000 /* dirsync behaviour (dir only) */ +/* these should be identical to their EXT4_*_FL counterparts, they are + * redefined here only to avoid dragging in fs/ext4/ext4.h */ +#define LUSTRE_SYNC_FL 0x00000008 /* Synchronous updates */ +#define LUSTRE_IMMUTABLE_FL 0x00000010 /* Immutable file */ +#define LUSTRE_APPEND_FL 0x00000020 /* writes to file may only append */ +#define LUSTRE_NOATIME_FL 0x00000080 /* do not update atime */ +#define LUSTRE_DIRSYNC_FL 0x00010000 /* dirsync behaviour (dir only) */ #ifdef __KERNEL__ -/* Convert wire MDS_*_FL to corresponding client local VFS S_* values - * for the client inode i_flags. The MDS_*_FL are the Lustre wire +/* Convert wire LUSTRE_*_FL to corresponding client local VFS S_* values + * for the client inode i_flags. The LUSTRE_*_FL are the Lustre wire * protocol equivalents of LDISKFS_*_FL values stored on disk, while * the S_* flags are kernel-internal values that change between kernel * versions. These flags are set/cleared via FSFILT_IOC_{GET,SET}_FLAGS. * See b=16526 for a full history. */ static inline int ll_ext_to_inode_flags(int flags) { - return (((flags & MDS_SYNC_FL) ? S_SYNC : 0) | - ((flags & MDS_NOATIME_FL) ? S_NOATIME : 0) | - ((flags & MDS_APPEND_FL) ? S_APPEND : 0) | + return (((flags & LUSTRE_SYNC_FL) ? S_SYNC : 0) | + ((flags & LUSTRE_NOATIME_FL) ? S_NOATIME : 0) | + ((flags & LUSTRE_APPEND_FL) ? S_APPEND : 0) | #if defined(S_DIRSYNC) - ((flags & MDS_DIRSYNC_FL) ? S_DIRSYNC : 0) | + ((flags & LUSTRE_DIRSYNC_FL) ? S_DIRSYNC : 0) | #endif - ((flags & MDS_IMMUTABLE_FL) ? S_IMMUTABLE : 0)); + ((flags & LUSTRE_IMMUTABLE_FL) ? S_IMMUTABLE : 0)); } static inline int ll_inode_to_ext_flags(int iflags) { - return (((iflags & S_SYNC) ? MDS_SYNC_FL : 0) | - ((iflags & S_NOATIME) ? MDS_NOATIME_FL : 0) | - ((iflags & S_APPEND) ? MDS_APPEND_FL : 0) | + return (((iflags & S_SYNC) ? LUSTRE_SYNC_FL : 0) | + ((iflags & S_NOATIME) ? LUSTRE_NOATIME_FL : 0) | + ((iflags & S_APPEND) ? LUSTRE_APPEND_FL : 0) | #if defined(S_DIRSYNC) - ((iflags & S_DIRSYNC) ? MDS_DIRSYNC_FL : 0) | + ((iflags & S_DIRSYNC) ? LUSTRE_DIRSYNC_FL : 0) | #endif - ((iflags & S_IMMUTABLE) ? MDS_IMMUTABLE_FL : 0)); + ((iflags & S_IMMUTABLE) ? LUSTRE_IMMUTABLE_FL : 0)); } #endif -/* - * while mds_body is to interact with 1.6, mdt_body is to interact with 2.0. - * both of them should have the same fields layout, because at client side - * one could be dynamically cast to the other. - * - * mdt_body has large size than mds_body, with unused padding (48 bytes) - * at the end. client always use size of mdt_body to prepare request/reply - * buffers, and actual data could be interepeted as mdt_body or mds_body - * accordingly. - */ -struct mds_body { - struct ll_fid fid1; - struct ll_fid fid2; - struct lustre_handle handle; - __u64 valid; - __u64 size; /* Offset, in the case of MDS_READPAGE */ - obd_time mtime; - obd_time atime; - obd_time ctime; - __u64 blocks; /* XID, in the case of MDS_READPAGE */ - __u64 io_epoch; - __u64 ino; - __u32 fsuid; - __u32 fsgid; - __u32 capability; - __u32 mode; - __u32 uid; - __u32 gid; - __u32 flags; /* from vfs for pin/unpin, MDS_BFLAG for close */ - __u32 rdev; - __u32 nlink; /* #bytes to read in the case of MDS_READPAGE */ - __u32 generation; - __u32 suppgid; - __u32 eadatasize; - __u32 aclsize; - __u32 max_mdsize; - __u32 max_cookiesize; - __u32 padding_4; /* also fix lustre_swab_mds_body */ -}; - -extern void lustre_swab_mds_body (struct mds_body *b); - struct mdt_body { struct lu_fid fid1; struct lu_fid fid2; @@ -1601,17 +2022,17 @@ struct mdt_body { obd_time ctime; __u64 blocks; /* XID, in the case of MDS_READPAGE */ __u64 ioepoch; - __u64 ino; /* for 1.6 compatibility */ + __u64 unused1; /* was "ino" until 2.4.0 */ __u32 fsuid; __u32 fsgid; __u32 capability; __u32 mode; __u32 uid; __u32 gid; - __u32 flags; /* from vfs for pin/unpin, MDS_BFLAG for close */ + __u32 flags; /* from vfs for pin/unpin, LUSTRE_BFLAG close */ __u32 rdev; __u32 nlink; /* #bytes to read in the case of MDS_READPAGE */ - __u32 generation; /* for 1.6 compatibility */ + __u32 unused2; /* was "generation" until 2.4.0 */ __u32 suppgid; __u32 eadatasize; __u32 aclsize; @@ -1638,86 +2059,6 @@ struct mdt_ioepoch { extern void lustre_swab_mdt_ioepoch (struct mdt_ioepoch *b); -#define Q_QUOTACHECK 0x800100 -#define Q_INITQUOTA 0x800101 /* init slave limits */ -#define Q_GETOINFO 0x800102 /* get obd quota info */ -#define Q_GETOQUOTA 0x800103 /* get obd quotas */ -#define Q_FINVALIDATE 0x800104 /* invalidate operational quotas */ - -#define Q_TYPEMATCH(id, type) \ - ((id) == (type) || (id) == UGQUOTA) - -#define Q_TYPESET(oqc, type) Q_TYPEMATCH((oqc)->qc_type, type) - -#define Q_GETOCMD(oqc) \ - ((oqc)->qc_cmd == Q_GETOINFO || (oqc)->qc_cmd == Q_GETOQUOTA) - -#define QCTL_COPY(out, in) \ -do { \ - Q_COPY(out, in, qc_cmd); \ - Q_COPY(out, in, qc_type); \ - Q_COPY(out, in, qc_id); \ - Q_COPY(out, in, qc_stat); \ - Q_COPY(out, in, qc_dqinfo); \ - Q_COPY(out, in, qc_dqblk); \ -} while (0) - -struct obd_quotactl { - __u32 qc_cmd; - __u32 qc_type; - __u32 qc_id; - __u32 qc_stat; - struct obd_dqinfo qc_dqinfo; - struct obd_dqblk qc_dqblk; -}; - -extern void lustre_swab_obd_quotactl(struct obd_quotactl *q); - -struct quota_adjust_qunit { - __u32 qaq_flags; - __u32 qaq_id; - __u64 qaq_bunit_sz; - __u64 qaq_iunit_sz; - __u64 padding1; -}; -extern void lustre_swab_quota_adjust_qunit(struct quota_adjust_qunit *q); - -/* flags is shared among quota structures */ -#define LQUOTA_FLAGS_GRP 1UL /* 0 is user, 1 is group */ -#define LQUOTA_FLAGS_BLK 2UL /* 0 is inode, 1 is block */ -#define LQUOTA_FLAGS_ADJBLK 4UL /* adjust the block qunit size */ -#define LQUOTA_FLAGS_ADJINO 8UL /* adjust the inode qunit size */ -#define LQUOTA_FLAGS_CHG_QS 16UL /* indicate whether it has capability of - * OBD_CONNECT_CHANGE_QS */ -#define LQUOTA_FLAGS_RECOVERY 32UL /* recovery is going on a uid/gid */ -#define LQUOTA_FLAGS_SETQUOTA 64UL /* being setquota on a uid/gid */ - -/* flags is specific for quota_adjust_qunit */ -#define LQUOTA_QAQ_CREATE_LQS (1 << 31) /* when it is set, need create lqs */ - -/* the status of lqs_flags in struct lustre_qunit_size */ -#define LQUOTA_QUNIT_FLAGS (LQUOTA_FLAGS_GRP | LQUOTA_FLAGS_BLK) - -#define QAQ_IS_GRP(qaq) ((qaq)->qaq_flags & LQUOTA_FLAGS_GRP) -#define QAQ_IS_ADJBLK(qaq) ((qaq)->qaq_flags & LQUOTA_FLAGS_ADJBLK) -#define QAQ_IS_ADJINO(qaq) ((qaq)->qaq_flags & LQUOTA_FLAGS_ADJINO) -#define QAQ_IS_CREATE_LQS(qaq) ((qaq)->qaq_flags & LQUOTA_QAQ_CREATE_LQS) - -#define QAQ_SET_GRP(qaq) ((qaq)->qaq_flags |= LQUOTA_FLAGS_GRP) -#define QAQ_SET_ADJBLK(qaq) ((qaq)->qaq_flags |= LQUOTA_FLAGS_ADJBLK) -#define QAQ_SET_ADJINO(qaq) ((qaq)->qaq_flags |= LQUOTA_FLAGS_ADJINO) -#define QAQ_SET_CREATE_LQS(qaq) ((qaq)->qaq_flags |= LQUOTA_QAQ_CREATE_LQS) - -/* inode access permission for remote user, the inode info are omitted, - * for client knows them. */ -struct mds_remote_perm { - __u32 rp_uid; - __u32 rp_gid; - __u32 rp_fsuid; - __u32 rp_fsgid; - __u32 rp_access_perm; /* MAY_READ/WRITE/EXEC */ -}; - /* permissions for md_perm.mp_perm */ enum { CFS_SETUID_PERM = 0x01, @@ -1727,8 +2068,8 @@ enum { CFS_RMTOWN_PERM = 0x10 }; -extern void lustre_swab_mds_remote_perm(struct mds_remote_perm *p); - +/* inode access permission for remote user, the inode info are omitted, + * for client knows them. */ struct mdt_remote_perm { __u32 rp_uid; __u32 rp_gid; @@ -1737,6 +2078,7 @@ struct mdt_remote_perm { __u32 rp_fsgid; __u32 rp_fsgid_h; __u32 rp_access_perm; /* MAY_READ/WRITE/EXEC */ + __u32 rp_padding; }; extern void lustre_swab_mdt_remote_perm(struct mdt_remote_perm *p); @@ -1763,7 +2105,7 @@ struct mdt_rec_setattr { obd_time sa_ctime; __u32 sa_attr_flags; __u32 sa_mode; - __u32 sa_padding_2; + __u32 sa_bias; /* some operation flags */ __u32 sa_padding_3; __u32 sa_padding_4; __u32 sa_padding_5; @@ -1799,18 +2141,18 @@ extern void lustre_swab_mdt_rec_setattr (struct mdt_rec_setattr *sa); #define FMODE_WRITE 00000002 #endif +#define MDS_FMODE_CLOSED 00000000 +#define MDS_FMODE_EXEC 00000004 /* IO Epoch is opened on a closed file. */ -#define FMODE_EPOCH 01000000 +#define MDS_FMODE_EPOCH 01000000 /* IO Epoch is opened on a file truncate. */ -#define FMODE_TRUNC 02000000 +#define MDS_FMODE_TRUNC 02000000 /* Size-on-MDS Attribute Update is pending. */ -#define FMODE_SOM 04000000 -#define FMODE_CLOSED 0 +#define MDS_FMODE_SOM 04000000 #define MDS_OPEN_CREATED 00000010 #define MDS_OPEN_CROSS 00000020 -#define MDS_FMODE_EXEC 00000004 #define MDS_OPEN_CREAT 00000100 #define MDS_OPEN_EXCL 00000200 #define MDS_OPEN_TRUNC 00001000 @@ -1818,6 +2160,7 @@ extern void lustre_swab_mdt_rec_setattr (struct mdt_rec_setattr *sa); #define MDS_OPEN_SYNC 00010000 #define MDS_OPEN_DIRECTORY 00200000 +#define MDS_OPEN_BY_FID 040000000 /* open_by_fid for known object */ #define MDS_OPEN_DELAY_CREATE 0100000000 /* delay initial object create */ #define MDS_OPEN_OWNEROVERRIDE 0200000000 /* NFSD rw-reopen ro file for owner */ #define MDS_OPEN_JOIN_FILE 0400000000 /* open for join file. @@ -1825,17 +2168,15 @@ extern void lustre_swab_mdt_rec_setattr (struct mdt_rec_setattr *sa); * anymore, reserve this flags * just for preventing such bit * to be reused. */ -#define MDS_CREATE_RMT_ACL 01000000000 /* indicate create on remote server - * with default ACL */ -#define MDS_CREATE_SLAVE_OBJ 02000000000 /* indicate create slave object - * actually, this is for create, not - * conflict with other open flags */ + #define MDS_OPEN_LOCK 04000000000 /* This open requires open lock */ #define MDS_OPEN_HAS_EA 010000000000 /* specify object create pattern */ #define MDS_OPEN_HAS_OBJS 020000000000 /* Just set the EA the obj exist */ #define MDS_OPEN_NORESTORE 0100000000000ULL /* Do not restore file at open */ #define MDS_OPEN_NEWSTRIPE 0200000000000ULL /* New stripe needed (restripe or * hsm restore) */ +#define MDS_OPEN_VOLATILE 0400000000000ULL /* File is volatile = created + unlinked */ /* permission for create non-directory file */ #define MAY_CREATE (1 << 7) @@ -1855,14 +2196,18 @@ extern void lustre_swab_mdt_rec_setattr (struct mdt_rec_setattr *sa); #define MAY_RGETFACL (1 << 14) enum { - MDS_CHECK_SPLIT = 1 << 0, - MDS_CROSS_REF = 1 << 1, - MDS_VTX_BYPASS = 1 << 2, - MDS_PERM_BYPASS = 1 << 3, - MDS_SOM = 1 << 4, - MDS_QUOTA_IGNORE = 1 << 5, - MDS_CLOSE_CLEANUP = 1 << 6, - MDS_KEEP_ORPHAN = 1 << 7 + MDS_CHECK_SPLIT = 1 << 0, + MDS_CROSS_REF = 1 << 1, + MDS_VTX_BYPASS = 1 << 2, + MDS_PERM_BYPASS = 1 << 3, + MDS_SOM = 1 << 4, + MDS_QUOTA_IGNORE = 1 << 5, + MDS_CLOSE_CLEANUP = 1 << 6, + MDS_KEEP_ORPHAN = 1 << 7, + MDS_RECOV_OPEN = 1 << 8, + MDS_DATA_MODIFIED = 1 << 9, + MDS_CREATE_VOLATILE = 1 << 10, + MDS_OWNEROVERRIDE = 1 << 11, }; /* instance of mdt_reint_rec */ @@ -1891,7 +2236,7 @@ struct mdt_rec_create { * extend cr_flags size without breaking 1.8 compat */ __u32 cr_flags_l; /* for use with open, low 32 bits */ __u32 cr_flags_h; /* for use with open, high 32 bits */ - __u32 cr_padding_3; /* rr_padding_3 */ + __u32 cr_umask; /* umask for create */ __u32 cr_padding_4; /* rr_padding_4 */ }; @@ -2089,13 +2434,6 @@ extern void lustre_swab_lmv_stripe_md(struct lmv_stripe_md *mea); #define MAX_HASH_SIZE 0x7fffffffffffffffULL #define MAX_HASH_HIGHEST_BIT 0x1000000000000000ULL -struct md_fld { - seqno_t mf_seq; - mdsno_t mf_mds; -}; - -extern void lustre_swab_md_fld (struct md_fld *mf); - enum fld_rpc_opc { FLD_QUERY = 900, FLD_LAST_OPC, @@ -2117,11 +2455,6 @@ enum seq_op { * LOV data structures */ -#define LOV_MIN_STRIPE_BITS 16 /* maximum PAGE_SIZE (ia64), power of 2 */ -#define LOV_MIN_STRIPE_SIZE (1<start <= ex2->end) && (ex2->start <= ex1->end); } +/* check if @ex1 contains @ex2 */ +static inline int ldlm_extent_contain(struct ldlm_extent *ex1, + struct ldlm_extent *ex2) +{ + return (ex1->start <= ex2->start) && (ex1->end >= ex2->end); +} + struct ldlm_inodebits { __u64 bits; }; @@ -2235,6 +2581,12 @@ typedef union { extern void lustre_swab_ldlm_policy_data (ldlm_wire_policy_data_t *d); +union ldlm_gl_desc { + struct ldlm_gl_lquota_desc lquota_desc; +}; + +extern void lustre_swab_gl_desc(union ldlm_gl_desc *); + struct ldlm_intent { __u64 opc; }; @@ -2292,6 +2644,9 @@ struct ldlm_reply { extern void lustre_swab_ldlm_reply (struct ldlm_reply *r); +#define ldlm_flags_to_wire(flags) ((__u32)(flags)) +#define ldlm_flags_from_wire(flags) ((__u64)(flags)) + /* * Opcodes for mountconf (mgs and mgc) */ @@ -2302,6 +2657,7 @@ typedef enum { MGS_TARGET_REG, /* whenever target starts up */ MGS_TARGET_DEL, MGS_SET_INFO, + MGS_CONFIG_READ, MGS_LAST_OPC } mgs_cmd_t; #define MGS_FIRST_OPC MGS_CONNECT @@ -2314,25 +2670,55 @@ struct mgs_send_param { }; /* We pass this info to the MGS so it can write config logs */ -#define MTI_NAME_MAXLEN 64 +#define MTI_NAME_MAXLEN 64 #define MTI_PARAM_MAXLEN 4096 -#define MTI_NIDS_MAX 32 +#define MTI_NIDS_MAX 32 struct mgs_target_info { __u32 mti_lustre_ver; __u32 mti_stripe_index; __u32 mti_config_ver; __u32 mti_flags; __u32 mti_nid_count; - __u32 padding; /* 64 bit align */ + __u32 mti_instance; /* Running instance of target */ char mti_fsname[MTI_NAME_MAXLEN]; char mti_svname[MTI_NAME_MAXLEN]; char mti_uuid[sizeof(struct obd_uuid)]; __u64 mti_nids[MTI_NIDS_MAX]; /* host nids (lnet_nid_t)*/ char mti_params[MTI_PARAM_MAXLEN]; }; - extern void lustre_swab_mgs_target_info(struct mgs_target_info *oinfo); +struct mgs_nidtbl_entry { + __u64 mne_version; /* table version of this entry */ + __u32 mne_instance; /* target instance # */ + __u32 mne_index; /* target index */ + __u32 mne_length; /* length of this entry - by bytes */ + __u8 mne_type; /* target type LDD_F_SV_TYPE_OST/MDT */ + __u8 mne_nid_type; /* type of nid(mbz). for ipv6. */ + __u8 mne_nid_size; /* size of each NID, by bytes */ + __u8 mne_nid_count; /* # of NIDs in buffer */ + union { + lnet_nid_t nids[0]; /* variable size buffer for NIDs. */ + } u; +}; +extern void lustre_swab_mgs_nidtbl_entry(struct mgs_nidtbl_entry *oinfo); + +struct mgs_config_body { + char mcb_name[MTI_NAME_MAXLEN]; /* logname */ + __u64 mcb_offset; /* next index of config log to request */ + __u16 mcb_type; /* type of log: CONFIG_T_[CONFIG|RECOVER] */ + __u8 mcb_reserved; + __u8 mcb_bits; /* bits unit size of config log */ + __u32 mcb_units; /* # of units for bulk transfer */ +}; +extern void lustre_swab_mgs_config_body(struct mgs_config_body *body); + +struct mgs_config_res { + __u64 mcr_offset; /* index of last config log */ + __u64 mcr_size; /* size of the log */ +}; +extern void lustre_swab_mgs_config_res(struct mgs_config_res *body); + /* Config marker flags (in config log) */ #define CM_START 0x01 #define CM_END 0x02 @@ -2345,7 +2731,7 @@ struct cfg_marker { __u32 cm_step; /* aka config version */ __u32 cm_flags; __u32 cm_vers; /* lustre release version number */ - __u32 padding; /* 64 bit align */ + __u32 cm_padding; /* 64 bit align */ obd_time cm_createtime; /*when this record was first created */ obd_time cm_canceltime; /*when this record is no longer valid*/ char cm_tgtname[MTI_NAME_MAXLEN]; @@ -2363,6 +2749,7 @@ typedef enum { OBD_PING = 400, OBD_LOG_CANCEL, OBD_QC_CALLBACK, + OBD_IDX_READ, OBD_LAST_OPC } obd_cmd_t; #define OBD_FIRST_OPC OBD_PING @@ -2392,111 +2779,100 @@ struct llog_catid { #define LLOG_OP_MASK 0xfff00000 typedef enum { - LLOG_PAD_MAGIC = LLOG_OP_MAGIC | 0x00000, - OST_SZ_REC = LLOG_OP_MAGIC | 0x00f00, - OST_RAID1_REC = LLOG_OP_MAGIC | 0x01000, - MDS_UNLINK_REC = LLOG_OP_MAGIC | 0x10000 | (MDS_REINT << 8) | REINT_UNLINK, - MDS_SETATTR_REC = LLOG_OP_MAGIC | 0x10000 | (MDS_REINT << 8) | REINT_SETATTR, - MDS_SETATTR64_REC = LLOG_OP_MAGIC | 0x90000 | (MDS_REINT << 8) | REINT_SETATTR, - OBD_CFG_REC = LLOG_OP_MAGIC | 0x20000, - PTL_CFG_REC = LLOG_OP_MAGIC | 0x30000, /* obsolete */ - LLOG_GEN_REC = LLOG_OP_MAGIC | 0x40000, - LLOG_JOIN_REC = LLOG_OP_MAGIC | 0x50000, /* obsolete */ - CHANGELOG_REC = LLOG_OP_MAGIC | 0x60000, - CHANGELOG_USER_REC = LLOG_OP_MAGIC | 0x70000, - LLOG_HDR_MAGIC = LLOG_OP_MAGIC | 0x45539, - LLOG_LOGID_MAGIC = LLOG_OP_MAGIC | 0x4553b, + LLOG_PAD_MAGIC = LLOG_OP_MAGIC | 0x00000, + OST_SZ_REC = LLOG_OP_MAGIC | 0x00f00, + /* OST_RAID1_REC = LLOG_OP_MAGIC | 0x01000, never used */ + MDS_UNLINK_REC = LLOG_OP_MAGIC | 0x10000 | (MDS_REINT << 8) | + REINT_UNLINK, /* obsolete after 2.5.0 */ + MDS_UNLINK64_REC = LLOG_OP_MAGIC | 0x90000 | (MDS_REINT << 8) | + REINT_UNLINK, + /* MDS_SETATTR_REC = LLOG_OP_MAGIC | 0x12401, obsolete 1.8.0 */ + MDS_SETATTR64_REC = LLOG_OP_MAGIC | 0x90000 | (MDS_REINT << 8) | + REINT_SETATTR, + OBD_CFG_REC = LLOG_OP_MAGIC | 0x20000, + /* PTL_CFG_REC = LLOG_OP_MAGIC | 0x30000, obsolete 1.4.0 */ + LLOG_GEN_REC = LLOG_OP_MAGIC | 0x40000, + /* LLOG_JOIN_REC = LLOG_OP_MAGIC | 0x50000, obsolete 1.8.0 */ + CHANGELOG_REC = LLOG_OP_MAGIC | 0x60000, + CHANGELOG_USER_REC = LLOG_OP_MAGIC | 0x70000, + LLOG_HDR_MAGIC = LLOG_OP_MAGIC | 0x45539, + LLOG_LOGID_MAGIC = LLOG_OP_MAGIC | 0x4553b, } llog_op_type; -/* - * for now, continue to support old pad records which have 0 for their - * type but still need to be swabbed for their length - */ -#define LLOG_REC_HDR_NEEDS_SWABBING(r) \ - (((r)->lrh_type & __swab32(LLOG_OP_MASK)) == \ - __swab32(LLOG_OP_MAGIC) || \ - (((r)->lrh_type == 0) && ((r)->lrh_len > LLOG_CHUNK_SIZE))) +#define LLOG_REC_HDR_NEEDS_SWABBING(r) \ + (((r)->lrh_type & __swab32(LLOG_OP_MASK)) == __swab32(LLOG_OP_MAGIC)) /** Log record header - stored in little endian order. * Each record must start with this struct, end with a llog_rec_tail, * and be a multiple of 256 bits in size. */ struct llog_rec_hdr { - __u32 lrh_len; - __u32 lrh_index; - __u32 lrh_type; - __u32 padding; + __u32 lrh_len; + __u32 lrh_index; + __u32 lrh_type; + __u32 lrh_id; }; struct llog_rec_tail { - __u32 lrt_len; - __u32 lrt_index; + __u32 lrt_len; + __u32 lrt_index; }; -struct llog_logid_rec { - struct llog_rec_hdr lid_hdr; - struct llog_logid lid_id; - __u32 padding1; - __u32 padding2; - __u32 padding3; - __u32 padding4; - __u32 padding5; - struct llog_rec_tail lid_tail; -} __attribute__((packed)); +/* Where data follow just after header */ +#define REC_DATA(ptr) \ + ((void *)((char *)ptr + sizeof(struct llog_rec_hdr))) -struct llog_create_rec { - struct llog_rec_hdr lcr_hdr; - struct ll_fid lcr_fid; - obd_id lcr_oid; - obd_count lcr_oseq; - __u32 padding; - struct llog_rec_tail lcr_tail; -} __attribute__((packed)); +#define REC_DATA_LEN(rec) \ + (rec->lrh_len - sizeof(struct llog_rec_hdr) - \ + sizeof(struct llog_rec_tail)) -struct llog_orphan_rec { - struct llog_rec_hdr lor_hdr; - obd_id lor_oid; - obd_count lor_ogen; - __u32 padding; - struct llog_rec_tail lor_tail; +struct llog_logid_rec { + struct llog_rec_hdr lid_hdr; + struct llog_logid lid_id; + __u32 lid_padding1; + __u64 lid_padding2; + __u64 lid_padding3; + struct llog_rec_tail lid_tail; } __attribute__((packed)); struct llog_unlink_rec { - struct llog_rec_hdr lur_hdr; - obd_id lur_oid; - obd_count lur_oseq; - obd_count lur_count; - struct llog_rec_tail lur_tail; + struct llog_rec_hdr lur_hdr; + obd_id lur_oid; + obd_count lur_oseq; + obd_count lur_count; + struct llog_rec_tail lur_tail; } __attribute__((packed)); -struct llog_setattr_rec { - struct llog_rec_hdr lsr_hdr; - obd_id lsr_oid; - obd_count lsr_oseq; - __u32 lsr_uid; - __u32 lsr_gid; - __u32 padding; - struct llog_rec_tail lsr_tail; +struct llog_unlink64_rec { + struct llog_rec_hdr lur_hdr; + struct lu_fid lur_fid; + obd_count lur_count; /* to destroy the lost precreated */ + __u32 lur_padding1; + __u64 lur_padding2; + __u64 lur_padding3; + struct llog_rec_tail lur_tail; } __attribute__((packed)); struct llog_setattr64_rec { - struct llog_rec_hdr lsr_hdr; - obd_id lsr_oid; - obd_count lsr_oseq; - __u32 padding; - __u32 lsr_uid; - __u32 lsr_uid_h; - __u32 lsr_gid; - __u32 lsr_gid_h; - struct llog_rec_tail lsr_tail; + struct llog_rec_hdr lsr_hdr; + obd_id lsr_oid; + obd_seq lsr_oseq; + __u32 lsr_uid; + __u32 lsr_uid_h; + __u32 lsr_gid; + __u32 lsr_gid_h; + __u64 lsr_padding; + struct llog_rec_tail lsr_tail; } __attribute__((packed)); struct llog_size_change_rec { - struct llog_rec_hdr lsc_hdr; - struct ll_fid lsc_fid; - __u32 lsc_ioepoch; - __u32 padding; - struct llog_rec_tail lsc_tail; + struct llog_rec_hdr lsc_hdr; + struct ll_fid lsc_fid; + __u32 lsc_ioepoch; + __u32 lsc_padding1; + __u64 lsc_padding2; + __u64 lsc_padding3; + struct llog_rec_tail lsc_tail; } __attribute__((packed)); #define CHANGELOG_MAGIC 0xca103000 @@ -2506,7 +2882,7 @@ struct llog_size_change_rec { /** bits covering all \a changelog_rec_type's */ #define CHANGELOG_ALLMASK 0XFFFFFFFF /** default \a changelog_rec_type mask */ -#define CHANGELOG_DEFMASK CHANGELOG_ALLMASK & ~(1 << CL_ATIME) +#define CHANGELOG_DEFMASK CHANGELOG_ALLMASK & ~(1 << CL_ATIME | 1 << CL_CLOSE) /* changelog llog name, needed by client replicators */ #define CHANGELOG_CATALOG "changelog_catalog" @@ -2523,6 +2899,12 @@ struct llog_changelog_rec { struct llog_rec_tail cr_tail; /**< for_sizezof_only */ } __attribute__((packed)); +struct llog_changelog_ext_rec { + struct llog_rec_hdr cr_hdr; + struct changelog_ext_rec cr; + struct llog_rec_tail cr_tail; /**< for_sizezof_only */ +} __attribute__((packed)); + #define CHANGELOG_USER_PREFIX "cl" struct llog_changelog_user_rec { @@ -2533,16 +2915,21 @@ struct llog_changelog_user_rec { struct llog_rec_tail cur_tail; } __attribute__((packed)); +/* Old llog gen for compatibility */ struct llog_gen { - __u64 mnt_cnt; - __u64 conn_cnt; + __u64 mnt_cnt; + __u64 conn_cnt; } __attribute__((packed)); struct llog_gen_rec { - struct llog_rec_hdr lgr_hdr; - struct llog_gen lgr_gen; - struct llog_rec_tail lgr_tail; + struct llog_rec_hdr lgr_hdr; + struct llog_gen lgr_gen; + __u64 padding1; + __u64 padding2; + __u64 padding3; + struct llog_rec_tail lgr_tail; }; + /* On-disk header structure of each log object, stored in little endian order */ #define LLOG_CHUNK_SIZE 8192 #define LLOG_HEADER_SIZE (96) @@ -2551,9 +2938,11 @@ struct llog_gen_rec { #define LLOG_MIN_REC_SIZE (24) /* round(llog_rec_hdr + llog_rec_tail) */ /* flags for the logs */ -#define LLOG_F_ZAP_WHEN_EMPTY 0x1 -#define LLOG_F_IS_CAT 0x2 -#define LLOG_F_IS_PLAIN 0x4 +enum llog_flag { + LLOG_F_ZAP_WHEN_EMPTY = 0x1, + LLOG_F_IS_CAT = 0x2, + LLOG_F_IS_PLAIN = 0x4, +}; struct llog_log_hdr { struct llog_rec_hdr llh_hdr; @@ -2570,9 +2959,9 @@ struct llog_log_hdr { struct llog_rec_tail llh_tail; } __attribute__((packed)); -#define LLOG_BITMAP_SIZE(llh) ((llh->llh_hdr.lrh_len - \ - llh->llh_bitmap_offset - \ - sizeof(llh->llh_tail)) * 8) +#define LLOG_BITMAP_SIZE(llh) (__u32)((llh->llh_hdr.lrh_len - \ + llh->llh_bitmap_offset - \ + sizeof(llh->llh_tail)) * 8) /** log cookies are used to reference a specific log file and a record therein */ struct llog_cookie { @@ -2590,7 +2979,7 @@ enum llogd_rpc_ops { LLOG_ORIGIN_HANDLE_WRITE_REC = 504, LLOG_ORIGIN_HANDLE_CLOSE = 505, LLOG_ORIGIN_CONNECT = 506, - LLOG_CATINFO = 507, /* for lfs catinfo */ + LLOG_CATINFO = 507, /* deprecated */ LLOG_ORIGIN_HANDLE_PREV_BLOCK = 508, LLOG_ORIGIN_HANDLE_DESTROY = 509, /* for destroy llog object*/ LLOG_LAST_OPC, @@ -2633,19 +3022,25 @@ struct obdo { obd_flag o_flags; obd_count o_nlink; /* brw: checksum */ obd_count o_parent_oid; - obd_count o_misc; /* brw: o_dropped */ + obd_count o_misc; /* brw: o_dropped */ + __u64 o_ioepoch; /* epoch in ost writes */ __u32 o_stripe_idx; /* holds stripe idx */ __u32 o_parent_ver; - struct lustre_handle o_handle; /* brw: lock handle to prolong locks */ - struct llog_cookie o_lcookie; /* destroy: unlink cookie from MDS */ - - __u32 o_uid_h; - __u32 o_gid_h; - __u64 o_padding_3; - __u64 o_padding_4; - __u64 o_padding_5; - __u64 o_padding_6; + struct lustre_handle o_handle; /* brw: lock handle to prolong + * locks */ + struct llog_cookie o_lcookie; /* destroy: unlink cookie from + * MDS */ + __u32 o_uid_h; + __u32 o_gid_h; + + __u64 o_data_version; /* getattr: sum of iversion for + * each stripe. + * brw: grant space consumed on + * the client for the write */ + __u64 o_padding_4; + __u64 o_padding_5; + __u64 o_padding_6; }; #define o_id o_oi.oi_id @@ -2654,6 +3049,7 @@ struct obdo { #define o_undirty o_mode #define o_dropped o_misc #define o_cksum o_nlink +#define o_grant_used o_data_version static inline void lustre_set_wire_obdo(struct obdo *wobdo, struct obdo *lobdo) { @@ -2706,8 +3102,7 @@ extern void lustre_swab_lov_mds_md(struct lov_mds_md *lmm); extern void lustre_swab_llogd_body (struct llogd_body *d); extern void lustre_swab_llog_hdr (struct llog_log_hdr *h); extern void lustre_swab_llogd_conn_body (struct llogd_conn_body *d); -extern void lustre_swab_llog_rec(struct llog_rec_hdr *rec, - struct llog_rec_tail *tail); +extern void lustre_swab_llog_rec(struct llog_rec_hdr *rec); struct lustre_cfg; extern void lustre_swab_lustre_cfg(struct lustre_cfg *lcfg); @@ -2719,66 +3114,91 @@ void dump_obdo(struct obdo *oa); void dump_ost_body(struct ost_body *ob); void dump_rcs(__u32 *rc); -/* this will be used when OBD_CONNECT_CHANGE_QS is set */ -struct qunit_data { - /** - * ID appiles to (uid, gid) - */ - __u32 qd_id; - /** - * LQUOTA_FLAGS_* affect the responding bits - */ - __u32 qd_flags; - /** - * acquire/release count (bytes for block quota) - */ - __u64 qd_count; - /** - * when a master returns the reply to a slave, it will - * contain the current corresponding qunit size - */ - __u64 qd_qunit; - __u64 padding; -}; +#define IDX_INFO_MAGIC 0x3D37CC37 -#define QDATA_IS_GRP(qdata) ((qdata)->qd_flags & LQUOTA_FLAGS_GRP) -#define QDATA_IS_BLK(qdata) ((qdata)->qd_flags & LQUOTA_FLAGS_BLK) -#define QDATA_IS_ADJBLK(qdata) ((qdata)->qd_flags & LQUOTA_FLAGS_ADJBLK) -#define QDATA_IS_ADJINO(qdata) ((qdata)->qd_flags & LQUOTA_FLAGS_ADJINO) -#define QDATA_IS_CHANGE_QS(qdata) ((qdata)->qd_flags & LQUOTA_FLAGS_CHG_QS) +/* Index file transfer through the network. The server serializes the index into + * a byte stream which is sent to the client via a bulk transfer */ +struct idx_info { + __u32 ii_magic; -#define QDATA_SET_GRP(qdata) ((qdata)->qd_flags |= LQUOTA_FLAGS_GRP) -#define QDATA_SET_BLK(qdata) ((qdata)->qd_flags |= LQUOTA_FLAGS_BLK) -#define QDATA_SET_ADJBLK(qdata) ((qdata)->qd_flags |= LQUOTA_FLAGS_ADJBLK) -#define QDATA_SET_ADJINO(qdata) ((qdata)->qd_flags |= LQUOTA_FLAGS_ADJINO) -#define QDATA_SET_CHANGE_QS(qdata) ((qdata)->qd_flags |= LQUOTA_FLAGS_CHG_QS) + /* reply: see idx_info_flags below */ + __u32 ii_flags; -#define QDATA_CLR_GRP(qdata) ((qdata)->qd_flags &= ~LQUOTA_FLAGS_GRP) -#define QDATA_CLR_CHANGE_QS(qdata) ((qdata)->qd_flags &= ~LQUOTA_FLAGS_CHG_QS) + /* request & reply: number of lu_idxpage (to be) transferred */ + __u16 ii_count; + __u16 ii_pad0; -extern void lustre_swab_qdata(struct qunit_data *d); -extern struct qunit_data *quota_get_qdata(void *req, int is_req, int is_exp); -extern int quota_copy_qdata(void *request, struct qunit_data *qdata, - int is_req, int is_exp); + /* request: requested attributes passed down to the iterator API */ + __u32 ii_attrs; -typedef enum { - QUOTA_DQACQ = 601, - QUOTA_DQREL = 602, - QUOTA_LAST_OPC -} quota_cmd_t; -#define QUOTA_FIRST_OPC QUOTA_DQACQ + /* request & reply: index file identifier (FID) */ + struct lu_fid ii_fid; -#define QUOTA_REQUEST 1 -#define QUOTA_REPLY 0 -#define QUOTA_EXPORT 1 -#define QUOTA_IMPORT 0 + /* reply: version of the index file before starting to walk the index. + * Please note that the version can be modified at any time during the + * transfer */ + __u64 ii_version; -/* quota check function */ -#define QUOTA_RET_OK 0 /**< return successfully */ -#define QUOTA_RET_NOQUOTA 1 /**< not support quota */ -#define QUOTA_RET_NOLIMIT 2 /**< quota limit isn't set */ -#define QUOTA_RET_ACQUOTA 4 /**< need to acquire extra quota */ + /* request: hash to start with: + * reply: hash of the first entry of the first lu_idxpage and hash + * of the entry to read next if any */ + __u64 ii_hash_start; + __u64 ii_hash_end; + /* reply: size of keys in lu_idxpages, minimal one if II_FL_VARKEY is + * set */ + __u16 ii_keysize; + + /* reply: size of records in lu_idxpages, minimal one if II_FL_VARREC + * is set */ + __u16 ii_recsize; + + __u32 ii_pad1; + __u64 ii_pad2; + __u64 ii_pad3; +}; +extern void lustre_swab_idx_info(struct idx_info *ii); + +#define II_END_OFF MDS_DIR_END_OFF /* all entries have been read */ + +/* List of flags used in idx_info::ii_flags */ +enum idx_info_flags { + II_FL_NOHASH = 1 << 0, /* client doesn't care about hash value */ + II_FL_VARKEY = 1 << 1, /* keys can be of variable size */ + II_FL_VARREC = 1 << 2, /* records can be of variable size */ + II_FL_NONUNQ = 1 << 3, /* index supports non-unique keys */ +}; + +#define LIP_MAGIC 0x8A6D6B6C + +/* 4KB (= LU_PAGE_SIZE) container gathering key/record pairs */ +struct lu_idxpage { + /* 16-byte header */ + __u32 lip_magic; + __u16 lip_flags; + __u16 lip_nr; /* number of entries in the container */ + __u64 lip_pad0; /* additional padding for future use */ + + /* key/record pairs are stored in the remaining 4080 bytes. + * depending upon the flags in idx_info::ii_flags, each key/record + * pair might be preceded by: + * - a hash value + * - the key size (II_FL_VARKEY is set) + * - the record size (II_FL_VARREC is set) + * + * For the time being, we only support fixed-size key & record. */ + char lip_entries[0]; +}; +extern void lustre_swab_lip_header(struct lu_idxpage *lip); + +#define LIP_HDR_SIZE (offsetof(struct lu_idxpage, lip_entries)) + +/* Gather all possible type associated with a 4KB container */ +union lu_page { + struct lu_dirpage lp_dir; /* for MDS_READPAGE */ + struct lu_idxpage lp_idx; /* for OBD_IDX_READ */ + char lp_array[LU_PAGE_SIZE]; +}; /* security opcodes */ typedef enum { @@ -2901,6 +3321,136 @@ struct getinfo_fid2path { void lustre_swab_fid2path (struct getinfo_fid2path *gf); +enum { + LAYOUT_INTENT_ACCESS = 0, + LAYOUT_INTENT_READ = 1, + LAYOUT_INTENT_WRITE = 2, + LAYOUT_INTENT_GLIMPSE = 3, + LAYOUT_INTENT_TRUNC = 4, + LAYOUT_INTENT_RELEASE = 5, + LAYOUT_INTENT_RESTORE = 6 +}; + +/* enqueue layout lock with intent */ +struct layout_intent { + __u32 li_opc; /* intent operation for enqueue, read, write etc */ + __u32 li_flags; + __u64 li_start; + __u64 li_end; +}; + +void lustre_swab_layout_intent(struct layout_intent *li); + +/** + * On the wire version of hsm_progress structure. + * + * Contains the userspace hsm_progress and some internal fields. + */ +struct hsm_progress_kernel { + /* Field taken from struct hsm_progress */ + lustre_fid hpk_fid; + __u64 hpk_cookie; + struct hsm_extent hpk_extent; + __u16 hpk_flags; + __u16 hpk_errval; /* positive val */ + __u32 hpk_padding1; + /* Additional fields */ + __u64 hpk_data_version; + __u64 hpk_padding2; +} __attribute__((packed)); + +extern void lustre_swab_hsm_user_state(struct hsm_user_state *hus); +extern void lustre_swab_hsm_current_action(struct hsm_current_action *action); +extern void lustre_swab_hsm_progress_kernel(struct hsm_progress_kernel *hpk); +extern void lustre_swab_hsm_user_state(struct hsm_user_state *hus); +extern void lustre_swab_hsm_user_item(struct hsm_user_item *hui); +extern void lustre_swab_hsm_request(struct hsm_request *hr); + +/** + * These are object update opcode under UPDATE_OBJ, which is currently + * being used by cross-ref operations between MDT. + * + * During the cross-ref operation, the Master MDT, which the client send the + * request to, will disassembly the operation into object updates, then OSP + * will send these updates to the remote MDT to be executed. + * + * Update request format + * magic: UPDATE_BUFFER_MAGIC_V1 + * Count: How many updates in the req. + * bufs[0] : following are packets of object. + * update[0]: + * type: object_update_op, the op code of update + * fid: The object fid of the update. + * lens/bufs: other parameters of the update. + * update[1]: + * type: object_update_op, the op code of update + * fid: The object fid of the update. + * lens/bufs: other parameters of the update. + * .......... + * update[7]: type: object_update_op, the op code of update + * fid: The object fid of the update. + * lens/bufs: other parameters of the update. + * Current 8 maxim updates per object update request. + * + ******************************************************************* + * update reply format: + * + * ur_version: UPDATE_REPLY_V1 + * ur_count: The count of the reply, which is usually equal + * to the number of updates in the request. + * ur_lens: The reply lengths of each object update. + * + * replies: 1st update reply [4bytes_ret: other body] + * 2nd update reply [4bytes_ret: other body] + * ..... + * nth update reply [4bytes_ret: other body] + * + * For each reply of the update, the format would be + * result(4 bytes):Other stuff + */ + +#define UPDATE_MAX_OPS 10 +#define UPDATE_BUFFER_MAGIC_V1 0xBDDE0001 +#define UPDATE_BUFFER_MAGIC UPDATE_BUFFER_MAGIC_V1 +#define UPDATE_BUF_COUNT 8 +enum object_update_op { + OBJ_CREATE = 1, + OBJ_DESTROY = 2, + OBJ_REF_ADD = 3, + OBJ_REF_DEL = 4, + OBJ_ATTR_SET = 5, + OBJ_ATTR_GET = 6, + OBJ_XATTR_SET = 7, + OBJ_XATTR_GET = 8, + OBJ_INDEX_LOOKUP = 9, + OBJ_INDEX_INSERT = 10, + OBJ_INDEX_DELETE = 11, + OBJ_LAST +}; + +struct update { + __u32 u_type; + __u32 u_padding; + struct lu_fid u_fid; + __u32 u_lens[UPDATE_BUF_COUNT]; + __u32 u_bufs[0]; +}; + +struct update_buf { + __u32 ub_magic; + __u32 ub_count; + __u32 ub_bufs[0]; +}; + +#define UPDATE_REPLY_V1 0x00BD0001 +struct update_reply { + __u32 ur_version; + __u32 ur_count; + __u32 ur_lens[0]; +}; + +void lustre_swab_update_buf(struct update_buf *ub); +void lustre_swab_update_reply_buf(struct update_reply *ur); #endif /** @} lustreidl */