int ocfs2_refresh_slot_info(struct ocfs2_super *osb) { int ret; struct ocfs2_slot_info *si = osb->slot_info; if (si == NULL) return 0; BUG_ON(si->si_blocks == 0); BUG_ON(si->si_bh == NULL); trace_ocfs2_refresh_slot_info(si->si_blocks); /* * We pass -1 as blocknr because we expect all of si->si_bh to * be !NULL. Thus, ocfs2_read_blocks() will ignore blocknr. If * this is not true, the read of -1 (UINT64_MAX) will fail. */ ret = ocfs2_read_blocks(INODE_CACHE(si->si_inode), -1, si->si_blocks, si->si_bh, OCFS2_BH_IGNORE_CACHE, NULL); if (ret == 0) { spin_lock(&osb->osb_lock); ocfs2_update_slot_info(si); spin_unlock(&osb->osb_lock); } return ret; }
void ocfs2_put_slot(struct ocfs2_super *osb) { int status, slot_num; struct ocfs2_slot_info *si = osb->slot_info; if (!si) return; spin_lock(&osb->osb_lock); ocfs2_update_slot_info(si); slot_num = osb->slot_num; ocfs2_invalidate_slot(si, osb->slot_num); osb->slot_num = OCFS2_INVALID_SLOT; spin_unlock(&osb->osb_lock); status = ocfs2_update_disk_slot(osb, si, slot_num); if (status < 0) { mlog_errno(status); goto bail; } bail: ocfs2_free_slot_info(osb); }
int ocfs2_refresh_slot_info(struct ocfs2_super *osb) { int ret; struct ocfs2_slot_info *si = osb->slot_info; if (si == NULL) return 0; BUG_ON(si->si_blocks == 0); BUG_ON(si->si_bh == NULL); trace_ocfs2_refresh_slot_info(si->si_blocks); /* */ ret = ocfs2_read_blocks(INODE_CACHE(si->si_inode), -1, si->si_blocks, si->si_bh, OCFS2_BH_IGNORE_CACHE, NULL); if (ret == 0) { spin_lock(&osb->osb_lock); ocfs2_update_slot_info(si); spin_unlock(&osb->osb_lock); } return ret; }
void ocfs2_put_slot(struct ocfs2_super *osb) { int status; struct ocfs2_slot_info *si = osb->slot_info; if (!si) return; ocfs2_update_slot_info(si); spin_lock(&si->si_lock); __ocfs2_fill_slot(si, osb->slot_num, OCFS2_INVALID_SLOT); osb->slot_num = OCFS2_INVALID_SLOT; spin_unlock(&si->si_lock); status = ocfs2_update_disk_slots(osb, si); if (status < 0) { mlog_errno(status); goto bail; } bail: osb->slot_info = NULL; ocfs2_free_slot_info(si); }
int ocfs2_find_slot(struct ocfs2_super *osb) { int status; int slot; struct ocfs2_slot_info *si; si = osb->slot_info; spin_lock(&osb->osb_lock); ocfs2_update_slot_info(si); /* search for ourselves first and take the slot if it already * exists. Perhaps we need to mark this in a variable for our * own journal recovery? Possibly not, though we certainly * need to warn to the user */ slot = __ocfs2_node_num_to_slot(si, osb->node_num); if (slot < 0) { /* if no slot yet, then just take 1st available * one. */ slot = __ocfs2_find_empty_slot(si, osb->preferred_slot); if (slot < 0) { spin_unlock(&osb->osb_lock); mlog(ML_ERROR, "no free slots available!\n"); status = -EINVAL; goto bail; } } else printk(KERN_INFO "ocfs2: Slot %d on device (%s) was already " "allocated to this node!\n", slot, osb->dev_str); ocfs2_set_slot(si, slot, osb->node_num); osb->slot_num = slot; spin_unlock(&osb->osb_lock); trace_ocfs2_find_slot(osb->slot_num); status = ocfs2_update_disk_slot(osb, si, osb->slot_num); if (status < 0) { mlog_errno(status); /* * if write block failed, invalidate slot to avoid overwrite * slot during dismount in case another node rightly has mounted */ spin_lock(&osb->osb_lock); ocfs2_invalidate_slot(si, osb->slot_num); osb->slot_num = OCFS2_INVALID_SLOT; spin_unlock(&osb->osb_lock); } bail: return status; }
int ocfs2_find_slot(struct ocfs2_super *osb) { int status; s16 slot; struct ocfs2_slot_info *si; mlog_entry_void(); si = osb->slot_info; ocfs2_update_slot_info(si); spin_lock(&si->si_lock); /* search for ourselves first and take the slot if it already * exists. Perhaps we need to mark this in a variable for our * own journal recovery? Possibly not, though we certainly * need to warn to the user */ slot = __ocfs2_node_num_to_slot(si, osb->node_num); if (slot == OCFS2_INVALID_SLOT) { /* if no slot yet, then just take 1st available * one. */ slot = __ocfs2_find_empty_slot(si); if (slot == OCFS2_INVALID_SLOT) { spin_unlock(&si->si_lock); mlog(ML_ERROR, "no free slots available!\n"); status = -EINVAL; goto bail; } } else mlog(ML_NOTICE, "slot %d is already allocated to this node!\n", slot); __ocfs2_fill_slot(si, slot, osb->node_num); osb->slot_num = slot; spin_unlock(&si->si_lock); mlog(0, "taking node slot %d\n", osb->slot_num); status = ocfs2_update_disk_slots(osb, si); if (status < 0) mlog_errno(status); bail: mlog_exit(status); return status; }
int ocfs2_find_slot(struct ocfs2_super *osb) { int status; int slot; struct ocfs2_slot_info *si; si = osb->slot_info; spin_lock(&osb->osb_lock); ocfs2_update_slot_info(si); /* */ slot = __ocfs2_node_num_to_slot(si, osb->node_num); if (slot < 0) { /* */ slot = __ocfs2_find_empty_slot(si, osb->preferred_slot); if (slot < 0) { spin_unlock(&osb->osb_lock); mlog(ML_ERROR, "no free slots available!\n"); status = -EINVAL; goto bail; } } else printk(KERN_INFO "ocfs2: Slot %d on device (%s) was already " "allocated to this node!\n", slot, osb->dev_str); ocfs2_set_slot(si, slot, osb->node_num); osb->slot_num = slot; spin_unlock(&osb->osb_lock); trace_ocfs2_find_slot(osb->slot_num); status = ocfs2_update_disk_slot(osb, si, osb->slot_num); if (status < 0) mlog_errno(status); bail: return status; }