Message ID | 20211118231352.2051947-7-david@fromorbit.com (mailing list archive) |
---|---|
State | Deferred, archived |
Headers | show |
Series | xfs: rework xlog_write() | expand |
On 19 Nov 2021 at 04:43, Dave Chinner wrote: > From: Dave Chinner <dchinner@redhat.com> > > To include log op headers directly into the log iovec regions that > the ophdrs wrap, we need to move the buffer alignment code from > xlog_finish_iovec() to xlog_prepare_iovec(). This is because the > xlog_op_header is only 12 bytes long, and we need the buffer that > the caller formats their data into to be 8 byte aligned. > > Hence once we start prepending the ophdr in xlog_prepare_iovec(), we > are going to need to manage the padding directly to ensure that the > buffer pointer returned is correctly aligned. > Looks good. Reviewed-by: Chandan Babu R <chandan.babu@oracle.com> > Signed-off-by: Dave Chinner <dchinner@redhat.com> > Reviewed-by: Christoph Hellwig <hch@lst.de> > Reviewed-by: Darrick J. Wong <djwong@kernel.org> > Reviewed-by: Brian Foster <bfoster@redhat.com> > --- > fs/xfs/xfs_log.h | 25 ++++++++++++++----------- > 1 file changed, 14 insertions(+), 11 deletions(-) > > diff --git a/fs/xfs/xfs_log.h b/fs/xfs/xfs_log.h > index 09b8fe9994f2..d1fc43476166 100644 > --- a/fs/xfs/xfs_log.h > +++ b/fs/xfs/xfs_log.h > @@ -21,6 +21,16 @@ struct xfs_log_vec { > > #define XFS_LOG_VEC_ORDERED (-1) > > +/* > + * We need to make sure the buffer pointer returned is naturally aligned for the > + * biggest basic data type we put into it. We have already accounted for this > + * padding when sizing the buffer. > + * > + * However, this padding does not get written into the log, and hence we have to > + * track the space used by the log vectors separately to prevent log space hangs > + * due to inaccurate accounting (i.e. a leak) of the used log space through the > + * CIL context ticket. > + */ > static inline void * > xlog_prepare_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec **vecp, > uint type) > @@ -34,6 +44,9 @@ xlog_prepare_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec **vecp, > vec = &lv->lv_iovecp[0]; > } > > + if (!IS_ALIGNED(lv->lv_buf_len, sizeof(uint64_t))) > + lv->lv_buf_len = round_up(lv->lv_buf_len, sizeof(uint64_t)); > + > vec->i_type = type; > vec->i_addr = lv->lv_buf + lv->lv_buf_len; > > @@ -43,20 +56,10 @@ xlog_prepare_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec **vecp, > return vec->i_addr; > } > > -/* > - * We need to make sure the next buffer is naturally aligned for the biggest > - * basic data type we put into it. We already accounted for this padding when > - * sizing the buffer. > - * > - * However, this padding does not get written into the log, and hence we have to > - * track the space used by the log vectors separately to prevent log space hangs > - * due to inaccurate accounting (i.e. a leak) of the used log space through the > - * CIL context ticket. > - */ > static inline void > xlog_finish_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec *vec, int len) > { > - lv->lv_buf_len += round_up(len, sizeof(uint64_t)); > + lv->lv_buf_len += len; > lv->lv_bytes += len; > vec->i_len = len; > }
diff --git a/fs/xfs/xfs_log.h b/fs/xfs/xfs_log.h index 09b8fe9994f2..d1fc43476166 100644 --- a/fs/xfs/xfs_log.h +++ b/fs/xfs/xfs_log.h @@ -21,6 +21,16 @@ struct xfs_log_vec { #define XFS_LOG_VEC_ORDERED (-1) +/* + * We need to make sure the buffer pointer returned is naturally aligned for the + * biggest basic data type we put into it. We have already accounted for this + * padding when sizing the buffer. + * + * However, this padding does not get written into the log, and hence we have to + * track the space used by the log vectors separately to prevent log space hangs + * due to inaccurate accounting (i.e. a leak) of the used log space through the + * CIL context ticket. + */ static inline void * xlog_prepare_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec **vecp, uint type) @@ -34,6 +44,9 @@ xlog_prepare_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec **vecp, vec = &lv->lv_iovecp[0]; } + if (!IS_ALIGNED(lv->lv_buf_len, sizeof(uint64_t))) + lv->lv_buf_len = round_up(lv->lv_buf_len, sizeof(uint64_t)); + vec->i_type = type; vec->i_addr = lv->lv_buf + lv->lv_buf_len; @@ -43,20 +56,10 @@ xlog_prepare_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec **vecp, return vec->i_addr; } -/* - * We need to make sure the next buffer is naturally aligned for the biggest - * basic data type we put into it. We already accounted for this padding when - * sizing the buffer. - * - * However, this padding does not get written into the log, and hence we have to - * track the space used by the log vectors separately to prevent log space hangs - * due to inaccurate accounting (i.e. a leak) of the used log space through the - * CIL context ticket. - */ static inline void xlog_finish_iovec(struct xfs_log_vec *lv, struct xfs_log_iovec *vec, int len) { - lv->lv_buf_len += round_up(len, sizeof(uint64_t)); + lv->lv_buf_len += len; lv->lv_bytes += len; vec->i_len = len; }