struct nes_device *nesdev = nesvnic->nesdev;
        struct nes_adapter *nesadapter = nesdev->nesadapter;
        int i = 0;
+       int rc;
 
        /* free the resources */
        if (nesfmr->leaf_pbl_cnt == 0) {
        nesmr->ibmw.rkey = ibfmr->rkey;
        nesmr->ibmw.uobject = NULL;
 
-       if (nesfmr->nesmr.pbls_used != 0) {
+       rc = nes_dealloc_mw(&nesmr->ibmw);
+
+       if ((rc == 0) && (nesfmr->nesmr.pbls_used != 0)) {
                spin_lock_irqsave(&nesadapter->pbl_lock, flags);
                if (nesfmr->nesmr.pbl_4k) {
                        nesadapter->free_4kpbl += nesfmr->nesmr.pbls_used;
                spin_unlock_irqrestore(&nesadapter->pbl_lock, flags);
        }
 
-       return nes_dealloc_mw(&nesmr->ibmw);
+       return rc;
 }
 
 
                        stag, ret, cqp_request->major_code, cqp_request->minor_code);
        major_code = cqp_request->major_code;
        nes_put_cqp_request(nesdev, cqp_request);
-
+       if ((!ret || major_code) && pbl_count != 0) {
+               spin_lock_irqsave(&nesadapter->pbl_lock, flags);
+               if (pbl_count > 1)
+                       nesadapter->free_4kpbl += pbl_count+1;
+               else if (residual_page_count > 32)
+                       nesadapter->free_4kpbl += pbl_count;
+               else
+                       nesadapter->free_256pbl += pbl_count;
+               spin_unlock_irqrestore(&nesadapter->pbl_lock, flags);
+       }
        if (!ret)
                return -ETIME;
        else if (major_code)
        cqp_request->waiting = 1;
        cqp_wqe = &cqp_request->cqp_wqe;
 
-       spin_lock_irqsave(&nesadapter->pbl_lock, flags);
-       if (nesmr->pbls_used != 0) {
-               if (nesmr->pbl_4k) {
-                       nesadapter->free_4kpbl += nesmr->pbls_used;
-                       if (nesadapter->free_4kpbl > nesadapter->max_4kpbl) {
-                               printk(KERN_ERR PFX "free 4KB PBLs(%u) has exceeded the max(%u)\n",
-                                               nesadapter->free_4kpbl, nesadapter->max_4kpbl);
-                       }
-               } else {
-                       nesadapter->free_256pbl += nesmr->pbls_used;
-                       if (nesadapter->free_256pbl > nesadapter->max_256pbl) {
-                               printk(KERN_ERR PFX "free 256B PBLs(%u) has exceeded the max(%u)\n",
-                                               nesadapter->free_256pbl, nesadapter->max_256pbl);
-                       }
-               }
-       }
-
-       spin_unlock_irqrestore(&nesadapter->pbl_lock, flags);
        nes_fill_init_cqp_wqe(cqp_wqe, nesdev);
        set_wqe_32bit_value(cqp_wqe->wqe_words, NES_CQP_WQE_OPCODE_IDX,
                        NES_CQP_DEALLOCATE_STAG | NES_CQP_STAG_VA_TO |
                        " CQP Major:Minor codes = 0x%04X:0x%04X\n",
                        ib_mr->rkey, ret, cqp_request->major_code, cqp_request->minor_code);
 
-       nes_free_resource(nesadapter, nesadapter->allocated_mrs,
-                       (ib_mr->rkey & 0x0fffff00) >> 8);
-
-       kfree(nesmr);
-
        major_code = cqp_request->major_code;
        minor_code = cqp_request->minor_code;
 
                                " to destroy STag, ib_mr=%p, rkey = 0x%08X\n",
                                major_code, minor_code, ib_mr, ib_mr->rkey);
                return -EIO;
-       } else
-               return 0;
+       }
+
+       if (nesmr->pbls_used != 0) {
+               spin_lock_irqsave(&nesadapter->pbl_lock, flags);
+               if (nesmr->pbl_4k) {
+                       nesadapter->free_4kpbl += nesmr->pbls_used;
+                       if (nesadapter->free_4kpbl > nesadapter->max_4kpbl)
+                               printk(KERN_ERR PFX "free 4KB PBLs(%u) has "
+                                       "exceeded the max(%u)\n",
+                                       nesadapter->free_4kpbl,
+                                       nesadapter->max_4kpbl);
+               } else {
+                       nesadapter->free_256pbl += nesmr->pbls_used;
+                       if (nesadapter->free_256pbl > nesadapter->max_256pbl)
+                               printk(KERN_ERR PFX "free 256B PBLs(%u) has "
+                                       "exceeded the max(%u)\n",
+                                       nesadapter->free_256pbl,
+                                       nesadapter->max_256pbl);
+               }
+               spin_unlock_irqrestore(&nesadapter->pbl_lock, flags);
+       }
+       nes_free_resource(nesadapter, nesadapter->allocated_mrs,
+                       (ib_mr->rkey & 0x0fffff00) >> 8);
+
+       kfree(nesmr);
+
+       return 0;
 }