Print this page
5814 bpobj_iterate_impl(): Close a refcount leak iterating on a sublist.
Reviewed by: Prakash Surya <prakash.surya@delphix.com>
Reviewed by: Matthew Ahrens <mahrens@delphix.com>
Reviewed by: Paul Dagnelie <paul.dagnelie@delphix.com>
Reviewed by: Simon Klinkert <simon.klinkert@gmail.com>
Approved by: Gordon Ross <gwr@nexenta.com>
5812 assertion failed in zrl_tryenter(): zr_owner==NULL
Reviewed by: George Wilson <george@delphix.com>
Reviewed by: Alex Reece <alex@delphix.com>
Reviewed by: Will Andrews <will@freebsd.org>
Approved by: Gordon Ross <gwr@nexenta.com>
5810 zdb should print details of bpobj
Reviewed by: Prakash Surya <prakash.surya@delphix.com>
Reviewed by: Alex Reece <alex@delphix.com>
Reviewed by: George Wilson <george@delphix.com>
Reviewed by: Will Andrews <will@freebsd.org>
Reviewed by: Simon Klinkert <simon.klinkert@gmail.com>
Approved by: Gordon Ross <gwr@nexenta.com>
        
*** 174,189 ****
          bpo->bpo_havesubobj = (doi.doi_bonus_size > BPOBJ_SIZE_V1);
          bpo->bpo_phys = bpo->bpo_dbuf->db_data;
          return (0);
  }
  
- boolean_t
- bpobj_is_open(const bpobj_t *bpo)
- {
-         return (bpo->bpo_object != 0);
- }
- 
  void
  bpobj_close(bpobj_t *bpo)
  {
          /* Lame workaround for closing a bpobj that was never opened. */
          if (bpo->bpo_object == 0)
--- 174,183 ----
*** 198,212 ****
          bpo->bpo_object = 0;
  
          mutex_destroy(&bpo->bpo_lock);
  }
  
! boolean_t
! bpobj_is_empty(bpobj_t *bpo)
  {
!         return (bpo->bpo_phys->bpo_num_blkptrs == 0 &&
!             (!bpo->bpo_havesubobj || bpo->bpo_phys->bpo_num_subobjs == 0));
  }
  
  static int
  bpobj_iterate_impl(bpobj_t *bpo, bpobj_itor_t func, void *arg, dmu_tx_t *tx,
      boolean_t free)
--- 192,206 ----
          bpo->bpo_object = 0;
  
          mutex_destroy(&bpo->bpo_lock);
  }
  
! static boolean_t
! bpobj_hasentries(bpobj_t *bpo)
  {
!         return (bpo->bpo_phys->bpo_num_blkptrs != 0 ||
!             (bpo->bpo_havesubobj && bpo->bpo_phys->bpo_num_subobjs != 0));
  }
  
  static int
  bpobj_iterate_impl(bpobj_t *bpo, bpobj_itor_t func, void *arg, dmu_tx_t *tx,
      boolean_t free)
*** 215,227 ****
          int epb;
          int64_t i;
          int err = 0;
          dmu_buf_t *dbuf = NULL;
  
-         ASSERT(bpobj_is_open(bpo));
          mutex_enter(&bpo->bpo_lock);
  
          if (free)
                  dmu_buf_will_dirty(bpo->bpo_dbuf, tx);
  
          for (i = bpo->bpo_phys->bpo_num_blkptrs - 1; i >= 0; i--) {
                  blkptr_t *bparray;
--- 209,223 ----
          int epb;
          int64_t i;
          int err = 0;
          dmu_buf_t *dbuf = NULL;
  
          mutex_enter(&bpo->bpo_lock);
  
+         if (!bpobj_hasentries(bpo))
+                 goto out;
+ 
          if (free)
                  dmu_buf_will_dirty(bpo->bpo_dbuf, tx);
  
          for (i = bpo->bpo_phys->bpo_num_blkptrs - 1; i >= 0; i--) {
                  blkptr_t *bparray;
*** 347,357 ****
                      (i + 1) * sizeof (uint64_t), -1ULL, tx));
          }
  
  out:
          /* If there are no entries, there should be no bytes. */
!         if (bpobj_is_empty(bpo)) {
                  ASSERT0(bpo->bpo_phys->bpo_bytes);
                  ASSERT0(bpo->bpo_phys->bpo_comp);
                  ASSERT0(bpo->bpo_phys->bpo_uncomp);
          }
  
--- 343,353 ----
                      (i + 1) * sizeof (uint64_t), -1ULL, tx));
          }
  
  out:
          /* If there are no entries, there should be no bytes. */
!         if (!bpobj_hasentries(bpo)) {
                  ASSERT0(bpo->bpo_phys->bpo_bytes);
                  ASSERT0(bpo->bpo_phys->bpo_comp);
                  ASSERT0(bpo->bpo_phys->bpo_uncomp);
          }
  
*** 382,393 ****
  bpobj_enqueue_subobj(bpobj_t *bpo, uint64_t subobj, dmu_tx_t *tx)
  {
          bpobj_t subbpo;
          uint64_t used, comp, uncomp, subsubobjs;
  
-         ASSERT(bpobj_is_open(bpo));
-         ASSERT(subobj != 0);
          ASSERT(bpo->bpo_havesubobj);
          ASSERT(bpo->bpo_havecomp);
          ASSERT(bpo->bpo_object != dmu_objset_pool(bpo->bpo_os)->dp_empty_bpobj);
  
          if (subobj == dmu_objset_pool(bpo->bpo_os)->dp_empty_bpobj) {
--- 378,387 ----
*** 396,406 ****
          }
  
          VERIFY3U(0, ==, bpobj_open(&subbpo, bpo->bpo_os, subobj));
          VERIFY3U(0, ==, bpobj_space(&subbpo, &used, &comp, &uncomp));
  
!         if (bpobj_is_empty(&subbpo)) {
                  /* No point in having an empty subobj. */
                  bpobj_close(&subbpo);
                  bpobj_free(bpo->bpo_os, subobj, tx);
                  return;
          }
--- 390,400 ----
          }
  
          VERIFY3U(0, ==, bpobj_open(&subbpo, bpo->bpo_os, subobj));
          VERIFY3U(0, ==, bpobj_space(&subbpo, &used, &comp, &uncomp));
  
!         if (!bpobj_hasentries(&subbpo)) {
                  /* No point in having an empty subobj. */
                  bpobj_close(&subbpo);
                  bpobj_free(bpo->bpo_os, subobj, tx);
                  return;
          }
*** 470,480 ****
          blkptr_t stored_bp = *bp;
          uint64_t offset;
          int blkoff;
          blkptr_t *bparray;
  
-         ASSERT(bpobj_is_open(bpo));
          ASSERT(!BP_IS_HOLE(bp));
          ASSERT(bpo->bpo_object != dmu_objset_pool(bpo->bpo_os)->dp_empty_bpobj);
  
          if (BP_IS_EMBEDDED(bp)) {
                  /*
--- 464,473 ----
*** 556,566 ****
  }
  
  int
  bpobj_space(bpobj_t *bpo, uint64_t *usedp, uint64_t *compp, uint64_t *uncompp)
  {
-         ASSERT(bpobj_is_open(bpo));
          mutex_enter(&bpo->bpo_lock);
  
          *usedp = bpo->bpo_phys->bpo_bytes;
          if (bpo->bpo_havecomp) {
                  *compp = bpo->bpo_phys->bpo_comp;
--- 549,558 ----
*** 583,594 ****
      uint64_t *usedp, uint64_t *compp, uint64_t *uncompp)
  {
          struct space_range_arg sra = { 0 };
          int err;
  
-         ASSERT(bpobj_is_open(bpo));
- 
          /*
           * As an optimization, if they want the whole txg range, just
           * get bpo_bytes rather than iterating over the bps.
           */
          if (mintxg < TXG_INITIAL && maxtxg == UINT64_MAX && bpo->bpo_havecomp)
--- 575,584 ----