lfsck_namespace_shrink_linkea() may fall in dead loop if it tries
to delete XATTR_NAME_LINK.
Signed-off-by: Lai Siyao <lai.siyao@whamcloud.com>
Change-Id: I43e6e7917f8f89eb2cc873c8521cd3fbb528f495
Reviewed-on: https://review.whamcloud.com/33252
Tested-by: Jenkins
Tested-by: Maloo <hpdd-maloo@intel.com>
Reviewed-by: Andreas Dilger <adilger@whamcloud.com>
Reviewed-by: Hongchao Zhang <hongchao@whamcloud.com>
Reviewed-by: Oleg Drokin <green@whamcloud.com>
lfsck_namespace_filter_linkea_entry(&ldata_new, cname, pfid,
true);
lfsck_namespace_filter_linkea_entry(&ldata_new, cname, pfid,
true);
- if (buflen < ldata_new.ld_leh->leh_len) {
+ /*
+ * linkea may change because it doesn't take lock in the first read, if
+ * it becomes larger, restart from beginning.
+ */
+ if ((ldata_new.ld_leh->leh_reccount > 0 ||
+ unlikely(ldata_new.ld_leh->leh_overflow_time)) &&
+ buflen < ldata_new.ld_leh->leh_len) {
dt_write_unlock(env, obj);
dt_trans_stop(env, dev, th);
lfsck_buf_init(&linkea_buf, ldata_new.ld_buf->lb_buf,
ldata_new.ld_leh->leh_len);
dt_write_unlock(env, obj);
dt_trans_stop(env, dev, th);
lfsck_buf_init(&linkea_buf, ldata_new.ld_buf->lb_buf,
ldata_new.ld_leh->leh_len);
+ buflen = linkea_buf.lb_len;
- if (ldata_new.ld_leh->leh_reccount > 0 ||
- unlikely(ldata->ld_leh->leh_overflow_time))
rc = lfsck_links_write(env, obj, &ldata_new, th);
else
rc = dt_xattr_del(env, obj, XATTR_NAME_LINK, th);
rc = lfsck_links_write(env, obj, &ldata_new, th);
else
rc = dt_xattr_del(env, obj, XATTR_NAME_LINK, th);