spin_unlock(&inode->i_lock);
new_cap = kmalloc(sizeof(*cap), GFP_NOFS);
if (new_cap == NULL) {
- ceph_put_snap_realm(realm);
+ ceph_put_snap_realm(mdsc, realm);
return -ENOMEM;
}
goto retry;
ci->i_snap_realm = realm;
list_add(&ci->i_snap_realm_item, &realm->inodes_with_caps);
} else {
- ceph_put_snap_realm(realm);
+ ceph_put_snap_realm(mdsc, realm);
}
dout(10, "add_cap inode %p (%llx.%llx) cap %xh now %xh seq %d mds%d\n",
{
struct ceph_mds_session *session = cap->session;
struct ceph_inode_info *ci = cap->ci;
+ struct ceph_mds_client *mdsc = &ceph_client(ci->vfs_inode.i_sb)->mdsc;
dout(20, "__ceph_remove_cap %p from %p\n", cap, &ci->vfs_inode);
if (RB_EMPTY_ROOT(&ci->i_caps)) {
list_del_init(&ci->i_snap_realm_item);
- ceph_put_snap_realm(ci->i_snap_realm);
+ ceph_put_snap_realm(mdsc, ci->i_snap_realm);
ci->i_snap_realm = NULL;
return 1;
}
if (!realm)
return ERR_PTR(-ENOMEM);
radix_tree_insert(&mdsc->snap_realms, ino, realm);
- realm->nref = 1; /* in tree */
+ realm->nref = 0; /* tree does not take a ref */
realm->ino = ino;
INIT_LIST_HEAD(&realm->children);
INIT_LIST_HEAD(&realm->child_item);
/*
* caller must hold snap_rwsem for write
*/
-void ceph_put_snap_realm(struct ceph_snap_realm *realm)
+void ceph_put_snap_realm(struct ceph_mds_client *mdsc,
+ struct ceph_snap_realm *realm)
{
dout(20, "put_snap_realm %llx %p %d -> %d\n", realm->ino, realm,
realm->nref, realm->nref-1);
realm->nref--;
if (realm->nref == 0) {
+ radix_tree_delete(&mdsc->snap_realms, realm->ino);
kfree(realm->prior_parent_snaps);
kfree(realm->snaps);
ceph_put_snap_context(realm->cached_context);
parentino, parent);
if (realm->parent) {
list_del_init(&realm->child_item);
- ceph_put_snap_realm(realm->parent);
+ ceph_put_snap_realm(mdsc, realm->parent);
}
realm->parent_ino = parentino;
realm->parent = parent;
if (p == e && invalidate)
rebuild_snap_realms(realm);
- ceph_put_snap_realm(realm);
+ ceph_put_snap_realm(mdsc, realm);
if (p < e)
goto more;
if (IS_ERR(child))
continue;
adjust_snap_realm_parent(mdsc, child, realm->ino);
- ceph_put_snap_realm(child);
+ ceph_put_snap_realm(mdsc, child);
}
- ceph_put_snap_realm(realm);
+ ceph_put_snap_realm(mdsc, realm);
}
/*
continue;
ci = ceph_inode(inode);
spin_lock(&inode->i_lock);
- ceph_put_snap_realm(ci->i_snap_realm);
+ ceph_put_snap_realm(mdsc, ci->i_snap_realm);
list_add(&ci->i_snap_realm_item,
&realm->inodes_with_caps);
ci->i_snap_realm = realm;
}
}
- ceph_put_snap_realm(realm);
+ ceph_put_snap_realm(mdsc, realm);
up_write(&mdsc->snap_rwsem);
return;