summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--module/zfs/dmu_send.c16
1 files changed, 16 insertions, 0 deletions
diff --git a/module/zfs/dmu_send.c b/module/zfs/dmu_send.c
index dee4cd775..c63ab43e1 100644
--- a/module/zfs/dmu_send.c
+++ b/module/zfs/dmu_send.c
@@ -454,6 +454,22 @@ static int
dump_freeobjects(dmu_sendarg_t *dsp, uint64_t firstobj, uint64_t numobjs)
{
struct drr_freeobjects *drrfo = &(dsp->dsa_drr->drr_u.drr_freeobjects);
+ uint64_t maxobj = DNODES_PER_BLOCK *
+ (DMU_META_DNODE(dsp->dsa_os)->dn_maxblkid + 1);
+
+ /*
+ * ZoL < 0.7 does not handle large FREEOBJECTS records correctly,
+ * leading to zfs recv never completing. to avoid this issue, don't
+ * send FREEOBJECTS records for object IDs which cannot exist on the
+ * receiving side.
+ */
+ if (maxobj > 0) {
+ if (maxobj < firstobj)
+ return (0);
+
+ if (maxobj < firstobj + numobjs)
+ numobjs = maxobj - firstobj;
+ }
/*
* If there is a pending op, but it's not PENDING_FREEOBJECTS,