diff options
Diffstat (limited to 'fs/ocfs2')
-rw-r--r-- | fs/ocfs2/alloc.c | 689 | ||||
-rw-r--r-- | fs/ocfs2/alloc.h | 10 | ||||
-rw-r--r-- | fs/ocfs2/dir.c | 4 | ||||
-rw-r--r-- | fs/ocfs2/dlm/dlmdomain.c | 3 | ||||
-rw-r--r-- | fs/ocfs2/dlm/dlmlock.c | 2 | ||||
-rw-r--r-- | fs/ocfs2/dlm/dlmmaster.c | 18 | ||||
-rw-r--r-- | fs/ocfs2/file.c | 193 | ||||
-rw-r--r-- | fs/ocfs2/inode.c | 23 | ||||
-rw-r--r-- | fs/ocfs2/mmap.c | 48 | ||||
-rw-r--r-- | fs/ocfs2/namei.c | 21 | ||||
-rw-r--r-- | fs/ocfs2/refcounttree.c | 29 | ||||
-rw-r--r-- | fs/ocfs2/refcounttree.h | 4 | ||||
-rw-r--r-- | fs/ocfs2/super.c | 20 | ||||
-rw-r--r-- | fs/ocfs2/super.h | 7 |
14 files changed, 411 insertions, 660 deletions
diff --git a/fs/ocfs2/alloc.c b/fs/ocfs2/alloc.c index af2d1bd00d0a..215e12ce1d85 100644 --- a/fs/ocfs2/alloc.c +++ b/fs/ocfs2/alloc.c | |||
@@ -2210,8 +2210,8 @@ out: | |||
2210 | * | 2210 | * |
2211 | * Will return zero if the path passed in is already the leftmost path. | 2211 | * Will return zero if the path passed in is already the leftmost path. |
2212 | */ | 2212 | */ |
2213 | static int ocfs2_find_cpos_for_left_leaf(struct super_block *sb, | 2213 | int ocfs2_find_cpos_for_left_leaf(struct super_block *sb, |
2214 | struct ocfs2_path *path, u32 *cpos) | 2214 | struct ocfs2_path *path, u32 *cpos) |
2215 | { | 2215 | { |
2216 | int i, j, ret = 0; | 2216 | int i, j, ret = 0; |
2217 | u64 blkno; | 2217 | u64 blkno; |
@@ -5588,19 +5588,97 @@ out: | |||
5588 | return ret; | 5588 | return ret; |
5589 | } | 5589 | } |
5590 | 5590 | ||
5591 | /* | ||
5592 | * ocfs2_reserve_blocks_for_rec_trunc() would look basically the | ||
5593 | * same as ocfs2_lock_alloctors(), except for it accepts a blocks | ||
5594 | * number to reserve some extra blocks, and it only handles meta | ||
5595 | * data allocations. | ||
5596 | * | ||
5597 | * Currently, only ocfs2_remove_btree_range() uses it for truncating | ||
5598 | * and punching holes. | ||
5599 | */ | ||
5600 | static int ocfs2_reserve_blocks_for_rec_trunc(struct inode *inode, | ||
5601 | struct ocfs2_extent_tree *et, | ||
5602 | u32 extents_to_split, | ||
5603 | struct ocfs2_alloc_context **ac, | ||
5604 | int extra_blocks) | ||
5605 | { | ||
5606 | int ret = 0, num_free_extents; | ||
5607 | unsigned int max_recs_needed = 2 * extents_to_split; | ||
5608 | struct ocfs2_super *osb = OCFS2_SB(inode->i_sb); | ||
5609 | |||
5610 | *ac = NULL; | ||
5611 | |||
5612 | num_free_extents = ocfs2_num_free_extents(osb, et); | ||
5613 | if (num_free_extents < 0) { | ||
5614 | ret = num_free_extents; | ||
5615 | mlog_errno(ret); | ||
5616 | goto out; | ||
5617 | } | ||
5618 | |||
5619 | if (!num_free_extents || | ||
5620 | (ocfs2_sparse_alloc(osb) && num_free_extents < max_recs_needed)) | ||
5621 | extra_blocks += ocfs2_extend_meta_needed(et->et_root_el); | ||
5622 | |||
5623 | if (extra_blocks) { | ||
5624 | ret = ocfs2_reserve_new_metadata_blocks(osb, extra_blocks, ac); | ||
5625 | if (ret < 0) { | ||
5626 | if (ret != -ENOSPC) | ||
5627 | mlog_errno(ret); | ||
5628 | goto out; | ||
5629 | } | ||
5630 | } | ||
5631 | |||
5632 | out: | ||
5633 | if (ret) { | ||
5634 | if (*ac) { | ||
5635 | ocfs2_free_alloc_context(*ac); | ||
5636 | *ac = NULL; | ||
5637 | } | ||
5638 | } | ||
5639 | |||
5640 | return ret; | ||
5641 | } | ||
5642 | |||
5591 | int ocfs2_remove_btree_range(struct inode *inode, | 5643 | int ocfs2_remove_btree_range(struct inode *inode, |
5592 | struct ocfs2_extent_tree *et, | 5644 | struct ocfs2_extent_tree *et, |
5593 | u32 cpos, u32 phys_cpos, u32 len, | 5645 | u32 cpos, u32 phys_cpos, u32 len, int flags, |
5594 | struct ocfs2_cached_dealloc_ctxt *dealloc) | 5646 | struct ocfs2_cached_dealloc_ctxt *dealloc, |
5647 | u64 refcount_loc) | ||
5595 | { | 5648 | { |
5596 | int ret; | 5649 | int ret, credits = 0, extra_blocks = 0; |
5597 | u64 phys_blkno = ocfs2_clusters_to_blocks(inode->i_sb, phys_cpos); | 5650 | u64 phys_blkno = ocfs2_clusters_to_blocks(inode->i_sb, phys_cpos); |
5598 | struct ocfs2_super *osb = OCFS2_SB(inode->i_sb); | 5651 | struct ocfs2_super *osb = OCFS2_SB(inode->i_sb); |
5599 | struct inode *tl_inode = osb->osb_tl_inode; | 5652 | struct inode *tl_inode = osb->osb_tl_inode; |
5600 | handle_t *handle; | 5653 | handle_t *handle; |
5601 | struct ocfs2_alloc_context *meta_ac = NULL; | 5654 | struct ocfs2_alloc_context *meta_ac = NULL; |
5655 | struct ocfs2_refcount_tree *ref_tree = NULL; | ||
5656 | |||
5657 | if ((flags & OCFS2_EXT_REFCOUNTED) && len) { | ||
5658 | BUG_ON(!(OCFS2_I(inode)->ip_dyn_features & | ||
5659 | OCFS2_HAS_REFCOUNT_FL)); | ||
5660 | |||
5661 | ret = ocfs2_lock_refcount_tree(osb, refcount_loc, 1, | ||
5662 | &ref_tree, NULL); | ||
5663 | if (ret) { | ||
5664 | mlog_errno(ret); | ||
5665 | goto out; | ||
5666 | } | ||
5667 | |||
5668 | ret = ocfs2_prepare_refcount_change_for_del(inode, | ||
5669 | refcount_loc, | ||
5670 | phys_blkno, | ||
5671 | len, | ||
5672 | &credits, | ||
5673 | &extra_blocks); | ||
5674 | if (ret < 0) { | ||
5675 | mlog_errno(ret); | ||
5676 | goto out; | ||
5677 | } | ||
5678 | } | ||
5602 | 5679 | ||
5603 | ret = ocfs2_lock_allocators(inode, et, 0, 1, NULL, &meta_ac); | 5680 | ret = ocfs2_reserve_blocks_for_rec_trunc(inode, et, 1, &meta_ac, |
5681 | extra_blocks); | ||
5604 | if (ret) { | 5682 | if (ret) { |
5605 | mlog_errno(ret); | 5683 | mlog_errno(ret); |
5606 | return ret; | 5684 | return ret; |
@@ -5616,7 +5694,8 @@ int ocfs2_remove_btree_range(struct inode *inode, | |||
5616 | } | 5694 | } |
5617 | } | 5695 | } |
5618 | 5696 | ||
5619 | handle = ocfs2_start_trans(osb, ocfs2_remove_extent_credits(osb->sb)); | 5697 | handle = ocfs2_start_trans(osb, |
5698 | ocfs2_remove_extent_credits(osb->sb) + credits); | ||
5620 | if (IS_ERR(handle)) { | 5699 | if (IS_ERR(handle)) { |
5621 | ret = PTR_ERR(handle); | 5700 | ret = PTR_ERR(handle); |
5622 | mlog_errno(ret); | 5701 | mlog_errno(ret); |
@@ -5643,9 +5722,20 @@ int ocfs2_remove_btree_range(struct inode *inode, | |||
5643 | 5722 | ||
5644 | ocfs2_journal_dirty(handle, et->et_root_bh); | 5723 | ocfs2_journal_dirty(handle, et->et_root_bh); |
5645 | 5724 | ||
5646 | ret = ocfs2_truncate_log_append(osb, handle, phys_blkno, len); | 5725 | if (phys_blkno) { |
5647 | if (ret) | 5726 | if (flags & OCFS2_EXT_REFCOUNTED) |
5648 | mlog_errno(ret); | 5727 | ret = ocfs2_decrease_refcount(inode, handle, |
5728 | ocfs2_blocks_to_clusters(osb->sb, | ||
5729 | phys_blkno), | ||
5730 | len, meta_ac, | ||
5731 | dealloc, 1); | ||
5732 | else | ||
5733 | ret = ocfs2_truncate_log_append(osb, handle, | ||
5734 | phys_blkno, len); | ||
5735 | if (ret) | ||
5736 | mlog_errno(ret); | ||
5737 | |||
5738 | } | ||
5649 | 5739 | ||
5650 | out_commit: | 5740 | out_commit: |
5651 | ocfs2_commit_trans(osb, handle); | 5741 | ocfs2_commit_trans(osb, handle); |
@@ -5655,6 +5745,9 @@ out: | |||
5655 | if (meta_ac) | 5745 | if (meta_ac) |
5656 | ocfs2_free_alloc_context(meta_ac); | 5746 | ocfs2_free_alloc_context(meta_ac); |
5657 | 5747 | ||
5748 | if (ref_tree) | ||
5749 | ocfs2_unlock_refcount_tree(osb, ref_tree, 1); | ||
5750 | |||
5658 | return ret; | 5751 | return ret; |
5659 | } | 5752 | } |
5660 | 5753 | ||
@@ -6488,417 +6581,6 @@ static int ocfs2_cache_extent_block_free(struct ocfs2_cached_dealloc_ctxt *ctxt, | |||
6488 | le16_to_cpu(eb->h_suballoc_bit)); | 6581 | le16_to_cpu(eb->h_suballoc_bit)); |
6489 | } | 6582 | } |
6490 | 6583 | ||
6491 | /* This function will figure out whether the currently last extent | ||
6492 | * block will be deleted, and if it will, what the new last extent | ||
6493 | * block will be so we can update his h_next_leaf_blk field, as well | ||
6494 | * as the dinodes i_last_eb_blk */ | ||
6495 | static int ocfs2_find_new_last_ext_blk(struct inode *inode, | ||
6496 | unsigned int clusters_to_del, | ||
6497 | struct ocfs2_path *path, | ||
6498 | struct buffer_head **new_last_eb) | ||
6499 | { | ||
6500 | int next_free, ret = 0; | ||
6501 | u32 cpos; | ||
6502 | struct ocfs2_extent_rec *rec; | ||
6503 | struct ocfs2_extent_block *eb; | ||
6504 | struct ocfs2_extent_list *el; | ||
6505 | struct buffer_head *bh = NULL; | ||
6506 | |||
6507 | *new_last_eb = NULL; | ||
6508 | |||
6509 | /* we have no tree, so of course, no last_eb. */ | ||
6510 | if (!path->p_tree_depth) | ||
6511 | goto out; | ||
6512 | |||
6513 | /* trunc to zero special case - this makes tree_depth = 0 | ||
6514 | * regardless of what it is. */ | ||
6515 | if (OCFS2_I(inode)->ip_clusters == clusters_to_del) | ||
6516 | goto out; | ||
6517 | |||
6518 | el = path_leaf_el(path); | ||
6519 | BUG_ON(!el->l_next_free_rec); | ||
6520 | |||
6521 | /* | ||
6522 | * Make sure that this extent list will actually be empty | ||
6523 | * after we clear away the data. We can shortcut out if | ||
6524 | * there's more than one non-empty extent in the | ||
6525 | * list. Otherwise, a check of the remaining extent is | ||
6526 | * necessary. | ||
6527 | */ | ||
6528 | next_free = le16_to_cpu(el->l_next_free_rec); | ||
6529 | rec = NULL; | ||
6530 | if (ocfs2_is_empty_extent(&el->l_recs[0])) { | ||
6531 | if (next_free > 2) | ||
6532 | goto out; | ||
6533 | |||
6534 | /* We may have a valid extent in index 1, check it. */ | ||
6535 | if (next_free == 2) | ||
6536 | rec = &el->l_recs[1]; | ||
6537 | |||
6538 | /* | ||
6539 | * Fall through - no more nonempty extents, so we want | ||
6540 | * to delete this leaf. | ||
6541 | */ | ||
6542 | } else { | ||
6543 | if (next_free > 1) | ||
6544 | goto out; | ||
6545 | |||
6546 | rec = &el->l_recs[0]; | ||
6547 | } | ||
6548 | |||
6549 | if (rec) { | ||
6550 | /* | ||
6551 | * Check it we'll only be trimming off the end of this | ||
6552 | * cluster. | ||
6553 | */ | ||
6554 | if (le16_to_cpu(rec->e_leaf_clusters) > clusters_to_del) | ||
6555 | goto out; | ||
6556 | } | ||
6557 | |||
6558 | ret = ocfs2_find_cpos_for_left_leaf(inode->i_sb, path, &cpos); | ||
6559 | if (ret) { | ||
6560 | mlog_errno(ret); | ||
6561 | goto out; | ||
6562 | } | ||
6563 | |||
6564 | ret = ocfs2_find_leaf(INODE_CACHE(inode), path_root_el(path), cpos, &bh); | ||
6565 | if (ret) { | ||
6566 | mlog_errno(ret); | ||
6567 | goto out; | ||
6568 | } | ||
6569 | |||
6570 | eb = (struct ocfs2_extent_block *) bh->b_data; | ||
6571 | el = &eb->h_list; | ||
6572 | |||
6573 | /* ocfs2_find_leaf() gets the eb from ocfs2_read_extent_block(). | ||
6574 | * Any corruption is a code bug. */ | ||
6575 | BUG_ON(!OCFS2_IS_VALID_EXTENT_BLOCK(eb)); | ||
6576 | |||
6577 | *new_last_eb = bh; | ||
6578 | get_bh(*new_last_eb); | ||
6579 | mlog(0, "returning block %llu, (cpos: %u)\n", | ||
6580 | (unsigned long long)le64_to_cpu(eb->h_blkno), cpos); | ||
6581 | out: | ||
6582 | brelse(bh); | ||
6583 | |||
6584 | return ret; | ||
6585 | } | ||
6586 | |||
6587 | /* | ||
6588 | * Trim some clusters off the rightmost edge of a tree. Only called | ||
6589 | * during truncate. | ||
6590 | * | ||
6591 | * The caller needs to: | ||
6592 | * - start journaling of each path component. | ||
6593 | * - compute and fully set up any new last ext block | ||
6594 | */ | ||
6595 | static int ocfs2_trim_tree(struct inode *inode, struct ocfs2_path *path, | ||
6596 | handle_t *handle, struct ocfs2_truncate_context *tc, | ||
6597 | u32 clusters_to_del, u64 *delete_start, u8 *flags) | ||
6598 | { | ||
6599 | int ret, i, index = path->p_tree_depth; | ||
6600 | u32 new_edge = 0; | ||
6601 | u64 deleted_eb = 0; | ||
6602 | struct buffer_head *bh; | ||
6603 | struct ocfs2_extent_list *el; | ||
6604 | struct ocfs2_extent_rec *rec; | ||
6605 | |||
6606 | *delete_start = 0; | ||
6607 | *flags = 0; | ||
6608 | |||
6609 | while (index >= 0) { | ||
6610 | bh = path->p_node[index].bh; | ||
6611 | el = path->p_node[index].el; | ||
6612 | |||
6613 | mlog(0, "traveling tree (index = %d, block = %llu)\n", | ||
6614 | index, (unsigned long long)bh->b_blocknr); | ||
6615 | |||
6616 | BUG_ON(le16_to_cpu(el->l_next_free_rec) == 0); | ||
6617 | |||
6618 | if (index != | ||
6619 | (path->p_tree_depth - le16_to_cpu(el->l_tree_depth))) { | ||
6620 | ocfs2_error(inode->i_sb, | ||
6621 | "Inode %lu has invalid ext. block %llu", | ||
6622 | inode->i_ino, | ||
6623 | (unsigned long long)bh->b_blocknr); | ||
6624 | ret = -EROFS; | ||
6625 | goto out; | ||
6626 | } | ||
6627 | |||
6628 | find_tail_record: | ||
6629 | i = le16_to_cpu(el->l_next_free_rec) - 1; | ||
6630 | rec = &el->l_recs[i]; | ||
6631 | |||
6632 | mlog(0, "Extent list before: record %d: (%u, %u, %llu), " | ||
6633 | "next = %u\n", i, le32_to_cpu(rec->e_cpos), | ||
6634 | ocfs2_rec_clusters(el, rec), | ||
6635 | (unsigned long long)le64_to_cpu(rec->e_blkno), | ||
6636 | le16_to_cpu(el->l_next_free_rec)); | ||
6637 | |||
6638 | BUG_ON(ocfs2_rec_clusters(el, rec) < clusters_to_del); | ||
6639 | |||
6640 | if (le16_to_cpu(el->l_tree_depth) == 0) { | ||
6641 | /* | ||
6642 | * If the leaf block contains a single empty | ||
6643 | * extent and no records, we can just remove | ||
6644 | * the block. | ||
6645 | */ | ||
6646 | if (i == 0 && ocfs2_is_empty_extent(rec)) { | ||
6647 | memset(rec, 0, | ||
6648 | sizeof(struct ocfs2_extent_rec)); | ||
6649 | el->l_next_free_rec = cpu_to_le16(0); | ||
6650 | |||
6651 | goto delete; | ||
6652 | } | ||
6653 | |||
6654 | /* | ||
6655 | * Remove any empty extents by shifting things | ||
6656 | * left. That should make life much easier on | ||
6657 | * the code below. This condition is rare | ||
6658 | * enough that we shouldn't see a performance | ||
6659 | * hit. | ||
6660 | */ | ||
6661 | if (ocfs2_is_empty_extent(&el->l_recs[0])) { | ||
6662 | le16_add_cpu(&el->l_next_free_rec, -1); | ||
6663 | |||
6664 | for(i = 0; | ||
6665 | i < le16_to_cpu(el->l_next_free_rec); i++) | ||
6666 | el->l_recs[i] = el->l_recs[i + 1]; | ||
6667 | |||
6668 | memset(&el->l_recs[i], 0, | ||
6669 | sizeof(struct ocfs2_extent_rec)); | ||
6670 | |||
6671 | /* | ||
6672 | * We've modified our extent list. The | ||
6673 | * simplest way to handle this change | ||
6674 | * is to being the search from the | ||
6675 | * start again. | ||
6676 | */ | ||
6677 | goto find_tail_record; | ||
6678 | } | ||
6679 | |||
6680 | le16_add_cpu(&rec->e_leaf_clusters, -clusters_to_del); | ||
6681 | |||
6682 | /* | ||
6683 | * We'll use "new_edge" on our way back up the | ||
6684 | * tree to know what our rightmost cpos is. | ||
6685 | */ | ||
6686 | new_edge = le16_to_cpu(rec->e_leaf_clusters); | ||
6687 | new_edge += le32_to_cpu(rec->e_cpos); | ||
6688 | |||
6689 | /* | ||
6690 | * The caller will use this to delete data blocks. | ||
6691 | */ | ||
6692 | *delete_start = le64_to_cpu(rec->e_blkno) | ||
6693 | + ocfs2_clusters_to_blocks(inode->i_sb, | ||
6694 | le16_to_cpu(rec->e_leaf_clusters)); | ||
6695 | *flags = rec->e_flags; | ||
6696 | |||
6697 | /* | ||
6698 | * If it's now empty, remove this record. | ||
6699 | */ | ||
6700 | if (le16_to_cpu(rec->e_leaf_clusters) == 0) { | ||
6701 | memset(rec, 0, | ||
6702 | sizeof(struct ocfs2_extent_rec)); | ||
6703 | le16_add_cpu(&el->l_next_free_rec, -1); | ||
6704 | } | ||
6705 | } else { | ||
6706 | if (le64_to_cpu(rec->e_blkno) == deleted_eb) { | ||
6707 | memset(rec, 0, | ||
6708 | sizeof(struct ocfs2_extent_rec)); | ||
6709 | le16_add_cpu(&el->l_next_free_rec, -1); | ||
6710 | |||
6711 | goto delete; | ||
6712 | } | ||
6713 | |||
6714 | /* Can this actually happen? */ | ||
6715 | if (le16_to_cpu(el->l_next_free_rec) == 0) | ||
6716 | goto delete; | ||
6717 | |||
6718 | /* | ||
6719 | * We never actually deleted any clusters | ||
6720 | * because our leaf was empty. There's no | ||
6721 | * reason to adjust the rightmost edge then. | ||
6722 | */ | ||
6723 | if (new_edge == 0) | ||
6724 | goto delete; | ||
6725 | |||
6726 | rec->e_int_clusters = cpu_to_le32(new_edge); | ||
6727 | le32_add_cpu(&rec->e_int_clusters, | ||
6728 | -le32_to_cpu(rec->e_cpos)); | ||
6729 | |||
6730 | /* | ||
6731 | * A deleted child record should have been | ||
6732 | * caught above. | ||
6733 | */ | ||
6734 | BUG_ON(le32_to_cpu(rec->e_int_clusters) == 0); | ||
6735 | } | ||
6736 | |||
6737 | delete: | ||
6738 | ocfs2_journal_dirty(handle, bh); | ||
6739 | |||
6740 | mlog(0, "extent list container %llu, after: record %d: " | ||
6741 | "(%u, %u, %llu), next = %u.\n", | ||
6742 | (unsigned long long)bh->b_blocknr, i, | ||
6743 | le32_to_cpu(rec->e_cpos), ocfs2_rec_clusters(el, rec), | ||
6744 | (unsigned long long)le64_to_cpu(rec->e_blkno), | ||
6745 | le16_to_cpu(el->l_next_free_rec)); | ||
6746 | |||
6747 | /* | ||
6748 | * We must be careful to only attempt delete of an | ||
6749 | * extent block (and not the root inode block). | ||
6750 | */ | ||
6751 | if (index > 0 && le16_to_cpu(el->l_next_free_rec) == 0) { | ||
6752 | struct ocfs2_extent_block *eb = | ||
6753 | (struct ocfs2_extent_block *)bh->b_data; | ||
6754 | |||
6755 | /* | ||
6756 | * Save this for use when processing the | ||
6757 | * parent block. | ||
6758 | */ | ||
6759 | deleted_eb = le64_to_cpu(eb->h_blkno); | ||
6760 | |||
6761 | mlog(0, "deleting this extent block.\n"); | ||
6762 | |||
6763 | ocfs2_remove_from_cache(INODE_CACHE(inode), bh); | ||
6764 | |||
6765 | BUG_ON(ocfs2_rec_clusters(el, &el->l_recs[0])); | ||
6766 | BUG_ON(le32_to_cpu(el->l_recs[0].e_cpos)); | ||
6767 | BUG_ON(le64_to_cpu(el->l_recs[0].e_blkno)); | ||
6768 | |||
6769 | ret = ocfs2_cache_extent_block_free(&tc->tc_dealloc, eb); | ||
6770 | /* An error here is not fatal. */ | ||
6771 | if (ret < 0) | ||
6772 | mlog_errno(ret); | ||
6773 | } else { | ||
6774 | deleted_eb = 0; | ||
6775 | } | ||
6776 | |||
6777 | index--; | ||
6778 | } | ||
6779 | |||
6780 | ret = 0; | ||
6781 | out: | ||
6782 | return ret; | ||
6783 | } | ||
6784 | |||
6785 | static int ocfs2_do_truncate(struct ocfs2_super *osb, | ||
6786 | unsigned int clusters_to_del, | ||
6787 | struct inode *inode, | ||
6788 | struct buffer_head *fe_bh, | ||
6789 | handle_t *handle, | ||
6790 | struct ocfs2_truncate_context *tc, | ||
6791 | struct ocfs2_path *path, | ||
6792 | struct ocfs2_alloc_context *meta_ac) | ||
6793 | { | ||
6794 | int status; | ||
6795 | struct ocfs2_dinode *fe; | ||
6796 | struct ocfs2_extent_block *last_eb = NULL; | ||
6797 | struct ocfs2_extent_list *el; | ||
6798 | struct buffer_head *last_eb_bh = NULL; | ||
6799 | u64 delete_blk = 0; | ||
6800 | u8 rec_flags; | ||
6801 | |||
6802 | fe = (struct ocfs2_dinode *) fe_bh->b_data; | ||
6803 | |||
6804 | status = ocfs2_find_new_last_ext_blk(inode, clusters_to_del, | ||
6805 | path, &last_eb_bh); | ||
6806 | if (status < 0) { | ||
6807 | mlog_errno(status); | ||
6808 | goto bail; | ||
6809 | } | ||
6810 | |||
6811 | /* | ||
6812 | * Each component will be touched, so we might as well journal | ||
6813 | * here to avoid having to handle errors later. | ||
6814 | */ | ||
6815 | status = ocfs2_journal_access_path(INODE_CACHE(inode), handle, path); | ||
6816 | if (status < 0) { | ||
6817 | mlog_errno(status); | ||
6818 | goto bail; | ||
6819 | } | ||
6820 | |||
6821 | if (last_eb_bh) { | ||
6822 | status = ocfs2_journal_access_eb(handle, INODE_CACHE(inode), last_eb_bh, | ||
6823 | OCFS2_JOURNAL_ACCESS_WRITE); | ||
6824 | if (status < 0) { | ||
6825 | mlog_errno(status); | ||
6826 | goto bail; | ||
6827 | } | ||
6828 | |||
6829 | last_eb = (struct ocfs2_extent_block *) last_eb_bh->b_data; | ||
6830 | } | ||
6831 | |||
6832 | el = &(fe->id2.i_list); | ||
6833 | |||
6834 | /* | ||
6835 | * Lower levels depend on this never happening, but it's best | ||
6836 | * to check it up here before changing the tree. | ||
6837 | */ | ||
6838 | if (el->l_tree_depth && el->l_recs[0].e_int_clusters == 0) { | ||
6839 | ocfs2_error(inode->i_sb, | ||
6840 | "Inode %lu has an empty extent record, depth %u\n", | ||
6841 | inode->i_ino, le16_to_cpu(el->l_tree_depth)); | ||
6842 | status = -EROFS; | ||
6843 | goto bail; | ||
6844 | } | ||
6845 | |||
6846 | dquot_free_space_nodirty(inode, | ||
6847 | ocfs2_clusters_to_bytes(osb->sb, clusters_to_del)); | ||
6848 | spin_lock(&OCFS2_I(inode)->ip_lock); | ||
6849 | OCFS2_I(inode)->ip_clusters = le32_to_cpu(fe->i_clusters) - | ||
6850 | clusters_to_del; | ||
6851 | spin_unlock(&OCFS2_I(inode)->ip_lock); | ||
6852 | le32_add_cpu(&fe->i_clusters, -clusters_to_del); | ||
6853 | inode->i_blocks = ocfs2_inode_sector_count(inode); | ||
6854 | |||
6855 | status = ocfs2_trim_tree(inode, path, handle, tc, | ||
6856 | clusters_to_del, &delete_blk, &rec_flags); | ||
6857 | if (status) { | ||
6858 | mlog_errno(status); | ||
6859 | goto bail; | ||
6860 | } | ||
6861 | |||
6862 | if (le32_to_cpu(fe->i_clusters) == 0) { | ||
6863 | /* trunc to zero is a special case. */ | ||
6864 | el->l_tree_depth = 0; | ||
6865 | fe->i_last_eb_blk = 0; | ||
6866 | } else if (last_eb) | ||
6867 | fe->i_last_eb_blk = last_eb->h_blkno; | ||
6868 | |||
6869 | ocfs2_journal_dirty(handle, fe_bh); | ||
6870 | |||
6871 | if (last_eb) { | ||
6872 | /* If there will be a new last extent block, then by | ||
6873 | * definition, there cannot be any leaves to the right of | ||
6874 | * him. */ | ||
6875 | last_eb->h_next_leaf_blk = 0; | ||
6876 | ocfs2_journal_dirty(handle, last_eb_bh); | ||
6877 | } | ||
6878 | |||
6879 | if (delete_blk) { | ||
6880 | if (rec_flags & OCFS2_EXT_REFCOUNTED) | ||
6881 | status = ocfs2_decrease_refcount(inode, handle, | ||
6882 | ocfs2_blocks_to_clusters(osb->sb, | ||
6883 | delete_blk), | ||
6884 | clusters_to_del, meta_ac, | ||
6885 | &tc->tc_dealloc, 1); | ||
6886 | else | ||
6887 | status = ocfs2_truncate_log_append(osb, handle, | ||
6888 | delete_blk, | ||
6889 | clusters_to_del); | ||
6890 | if (status < 0) { | ||
6891 | mlog_errno(status); | ||
6892 | goto bail; | ||
6893 | } | ||
6894 | } | ||
6895 | status = 0; | ||
6896 | bail: | ||
6897 | brelse(last_eb_bh); | ||
6898 | mlog_exit(status); | ||
6899 | return status; | ||
6900 | } | ||
6901 | |||
6902 | static int ocfs2_zero_func(handle_t *handle, struct buffer_head *bh) | 6584 | static int ocfs2_zero_func(handle_t *handle, struct buffer_head *bh) |
6903 | { | 6585 | { |
6904 | set_buffer_uptodate(bh); | 6586 | set_buffer_uptodate(bh); |
@@ -7307,26 +6989,29 @@ out: | |||
7307 | */ | 6989 | */ |
7308 | int ocfs2_commit_truncate(struct ocfs2_super *osb, | 6990 | int ocfs2_commit_truncate(struct ocfs2_super *osb, |
7309 | struct inode *inode, | 6991 | struct inode *inode, |
7310 | struct buffer_head *fe_bh, | 6992 | struct buffer_head *di_bh) |
7311 | struct ocfs2_truncate_context *tc) | ||
7312 | { | 6993 | { |
7313 | int status, i, credits, tl_sem = 0; | 6994 | int status = 0, i, flags = 0; |
7314 | u32 clusters_to_del, new_highest_cpos, range; | 6995 | u32 new_highest_cpos, range, trunc_cpos, trunc_len, phys_cpos, coff; |
7315 | u64 blkno = 0; | 6996 | u64 blkno = 0; |
7316 | struct ocfs2_extent_list *el; | 6997 | struct ocfs2_extent_list *el; |
7317 | handle_t *handle = NULL; | 6998 | struct ocfs2_extent_rec *rec; |
7318 | struct inode *tl_inode = osb->osb_tl_inode; | ||
7319 | struct ocfs2_path *path = NULL; | 6999 | struct ocfs2_path *path = NULL; |
7320 | struct ocfs2_dinode *di = (struct ocfs2_dinode *)fe_bh->b_data; | 7000 | struct ocfs2_dinode *di = (struct ocfs2_dinode *)di_bh->b_data; |
7321 | struct ocfs2_alloc_context *meta_ac = NULL; | 7001 | struct ocfs2_extent_list *root_el = &(di->id2.i_list); |
7322 | struct ocfs2_refcount_tree *ref_tree = NULL; | 7002 | u64 refcount_loc = le64_to_cpu(di->i_refcount_loc); |
7003 | struct ocfs2_extent_tree et; | ||
7004 | struct ocfs2_cached_dealloc_ctxt dealloc; | ||
7323 | 7005 | ||
7324 | mlog_entry_void(); | 7006 | mlog_entry_void(); |
7325 | 7007 | ||
7008 | ocfs2_init_dinode_extent_tree(&et, INODE_CACHE(inode), di_bh); | ||
7009 | ocfs2_init_dealloc_ctxt(&dealloc); | ||
7010 | |||
7326 | new_highest_cpos = ocfs2_clusters_for_bytes(osb->sb, | 7011 | new_highest_cpos = ocfs2_clusters_for_bytes(osb->sb, |
7327 | i_size_read(inode)); | 7012 | i_size_read(inode)); |
7328 | 7013 | ||
7329 | path = ocfs2_new_path(fe_bh, &di->id2.i_list, | 7014 | path = ocfs2_new_path(di_bh, &di->id2.i_list, |
7330 | ocfs2_journal_access_di); | 7015 | ocfs2_journal_access_di); |
7331 | if (!path) { | 7016 | if (!path) { |
7332 | status = -ENOMEM; | 7017 | status = -ENOMEM; |
@@ -7345,8 +7030,6 @@ start: | |||
7345 | goto bail; | 7030 | goto bail; |
7346 | } | 7031 | } |
7347 | 7032 | ||
7348 | credits = 0; | ||
7349 | |||
7350 | /* | 7033 | /* |
7351 | * Truncate always works against the rightmost tree branch. | 7034 | * Truncate always works against the rightmost tree branch. |
7352 | */ | 7035 | */ |
@@ -7381,101 +7064,62 @@ start: | |||
7381 | } | 7064 | } |
7382 | 7065 | ||
7383 | i = le16_to_cpu(el->l_next_free_rec) - 1; | 7066 | i = le16_to_cpu(el->l_next_free_rec) - 1; |
7384 | range = le32_to_cpu(el->l_recs[i].e_cpos) + | 7067 | rec = &el->l_recs[i]; |
7385 | ocfs2_rec_clusters(el, &el->l_recs[i]); | 7068 | flags = rec->e_flags; |
7386 | if (i == 0 && ocfs2_is_empty_extent(&el->l_recs[i])) { | 7069 | range = le32_to_cpu(rec->e_cpos) + ocfs2_rec_clusters(el, rec); |
7387 | clusters_to_del = 0; | 7070 | |
7388 | } else if (le32_to_cpu(el->l_recs[i].e_cpos) >= new_highest_cpos) { | 7071 | if (i == 0 && ocfs2_is_empty_extent(rec)) { |
7389 | clusters_to_del = ocfs2_rec_clusters(el, &el->l_recs[i]); | 7072 | /* |
7390 | blkno = le64_to_cpu(el->l_recs[i].e_blkno); | 7073 | * Lower levels depend on this never happening, but it's best |
7074 | * to check it up here before changing the tree. | ||
7075 | */ | ||
7076 | if (root_el->l_tree_depth && rec->e_int_clusters == 0) { | ||
7077 | ocfs2_error(inode->i_sb, "Inode %lu has an empty " | ||
7078 | "extent record, depth %u\n", inode->i_ino, | ||
7079 | le16_to_cpu(root_el->l_tree_depth)); | ||
7080 | status = -EROFS; | ||
7081 | goto bail; | ||
7082 | } | ||
7083 | trunc_cpos = le32_to_cpu(rec->e_cpos); | ||
7084 | trunc_len = 0; | ||
7085 | blkno = 0; | ||
7086 | } else if (le32_to_cpu(rec->e_cpos) >= new_highest_cpos) { | ||
7087 | /* | ||
7088 | * Truncate entire record. | ||
7089 | */ | ||
7090 | trunc_cpos = le32_to_cpu(rec->e_cpos); | ||
7091 | trunc_len = ocfs2_rec_clusters(el, rec); | ||
7092 | blkno = le64_to_cpu(rec->e_blkno); | ||
7391 | } else if (range > new_highest_cpos) { | 7093 | } else if (range > new_highest_cpos) { |
7392 | clusters_to_del = (ocfs2_rec_clusters(el, &el->l_recs[i]) + | 7094 | /* |
7393 | le32_to_cpu(el->l_recs[i].e_cpos)) - | 7095 | * Partial truncate. it also should be |
7394 | new_highest_cpos; | 7096 | * the last truncate we're doing. |
7395 | blkno = le64_to_cpu(el->l_recs[i].e_blkno) + | 7097 | */ |
7396 | ocfs2_clusters_to_blocks(inode->i_sb, | 7098 | trunc_cpos = new_highest_cpos; |
7397 | ocfs2_rec_clusters(el, &el->l_recs[i]) - | 7099 | trunc_len = range - new_highest_cpos; |
7398 | clusters_to_del); | 7100 | coff = new_highest_cpos - le32_to_cpu(rec->e_cpos); |
7101 | blkno = le64_to_cpu(rec->e_blkno) + | ||
7102 | ocfs2_clusters_to_blocks(inode->i_sb, coff); | ||
7399 | } else { | 7103 | } else { |
7104 | /* | ||
7105 | * Truncate completed, leave happily. | ||
7106 | */ | ||
7400 | status = 0; | 7107 | status = 0; |
7401 | goto bail; | 7108 | goto bail; |
7402 | } | 7109 | } |
7403 | 7110 | ||
7404 | mlog(0, "clusters_to_del = %u in this pass, tail blk=%llu\n", | 7111 | phys_cpos = ocfs2_blocks_to_clusters(inode->i_sb, blkno); |
7405 | clusters_to_del, (unsigned long long)path_leaf_bh(path)->b_blocknr); | ||
7406 | |||
7407 | if (el->l_recs[i].e_flags & OCFS2_EXT_REFCOUNTED && clusters_to_del) { | ||
7408 | BUG_ON(!(OCFS2_I(inode)->ip_dyn_features & | ||
7409 | OCFS2_HAS_REFCOUNT_FL)); | ||
7410 | |||
7411 | status = ocfs2_lock_refcount_tree(osb, | ||
7412 | le64_to_cpu(di->i_refcount_loc), | ||
7413 | 1, &ref_tree, NULL); | ||
7414 | if (status) { | ||
7415 | mlog_errno(status); | ||
7416 | goto bail; | ||
7417 | } | ||
7418 | |||
7419 | status = ocfs2_prepare_refcount_change_for_del(inode, fe_bh, | ||
7420 | blkno, | ||
7421 | clusters_to_del, | ||
7422 | &credits, | ||
7423 | &meta_ac); | ||
7424 | if (status < 0) { | ||
7425 | mlog_errno(status); | ||
7426 | goto bail; | ||
7427 | } | ||
7428 | } | ||
7429 | |||
7430 | mutex_lock(&tl_inode->i_mutex); | ||
7431 | tl_sem = 1; | ||
7432 | /* ocfs2_truncate_log_needs_flush guarantees us at least one | ||
7433 | * record is free for use. If there isn't any, we flush to get | ||
7434 | * an empty truncate log. */ | ||
7435 | if (ocfs2_truncate_log_needs_flush(osb)) { | ||
7436 | status = __ocfs2_flush_truncate_log(osb); | ||
7437 | if (status < 0) { | ||
7438 | mlog_errno(status); | ||
7439 | goto bail; | ||
7440 | } | ||
7441 | } | ||
7442 | |||
7443 | credits += ocfs2_calc_tree_trunc_credits(osb->sb, clusters_to_del, | ||
7444 | (struct ocfs2_dinode *)fe_bh->b_data, | ||
7445 | el); | ||
7446 | handle = ocfs2_start_trans(osb, credits); | ||
7447 | if (IS_ERR(handle)) { | ||
7448 | status = PTR_ERR(handle); | ||
7449 | handle = NULL; | ||
7450 | mlog_errno(status); | ||
7451 | goto bail; | ||
7452 | } | ||
7453 | 7112 | ||
7454 | status = ocfs2_do_truncate(osb, clusters_to_del, inode, fe_bh, handle, | 7113 | status = ocfs2_remove_btree_range(inode, &et, trunc_cpos, |
7455 | tc, path, meta_ac); | 7114 | phys_cpos, trunc_len, flags, &dealloc, |
7115 | refcount_loc); | ||
7456 | if (status < 0) { | 7116 | if (status < 0) { |
7457 | mlog_errno(status); | 7117 | mlog_errno(status); |
7458 | goto bail; | 7118 | goto bail; |
7459 | } | 7119 | } |
7460 | 7120 | ||
7461 | mutex_unlock(&tl_inode->i_mutex); | ||
7462 | tl_sem = 0; | ||
7463 | |||
7464 | ocfs2_commit_trans(osb, handle); | ||
7465 | handle = NULL; | ||
7466 | |||
7467 | ocfs2_reinit_path(path, 1); | 7121 | ocfs2_reinit_path(path, 1); |
7468 | 7122 | ||
7469 | if (meta_ac) { | ||
7470 | ocfs2_free_alloc_context(meta_ac); | ||
7471 | meta_ac = NULL; | ||
7472 | } | ||
7473 | |||
7474 | if (ref_tree) { | ||
7475 | ocfs2_unlock_refcount_tree(osb, ref_tree, 1); | ||
7476 | ref_tree = NULL; | ||
7477 | } | ||
7478 | |||
7479 | /* | 7123 | /* |
7480 | * The check above will catch the case where we've truncated | 7124 | * The check above will catch the case where we've truncated |
7481 | * away all allocation. | 7125 | * away all allocation. |
@@ -7486,25 +7130,10 @@ bail: | |||
7486 | 7130 | ||
7487 | ocfs2_schedule_truncate_log_flush(osb, 1); | 7131 | ocfs2_schedule_truncate_log_flush(osb, 1); |
7488 | 7132 | ||
7489 | if (tl_sem) | 7133 | ocfs2_run_deallocs(osb, &dealloc); |
7490 | mutex_unlock(&tl_inode->i_mutex); | ||
7491 | |||
7492 | if (handle) | ||
7493 | ocfs2_commit_trans(osb, handle); | ||
7494 | |||
7495 | if (meta_ac) | ||
7496 | ocfs2_free_alloc_context(meta_ac); | ||
7497 | |||
7498 | if (ref_tree) | ||
7499 | ocfs2_unlock_refcount_tree(osb, ref_tree, 1); | ||
7500 | |||
7501 | ocfs2_run_deallocs(osb, &tc->tc_dealloc); | ||
7502 | 7134 | ||
7503 | ocfs2_free_path(path); | 7135 | ocfs2_free_path(path); |
7504 | 7136 | ||
7505 | /* This will drop the ext_alloc cluster lock for us */ | ||
7506 | ocfs2_free_truncate_context(tc); | ||
7507 | |||
7508 | mlog_exit(status); | 7137 | mlog_exit(status); |
7509 | return status; | 7138 | return status; |
7510 | } | 7139 | } |
diff --git a/fs/ocfs2/alloc.h b/fs/ocfs2/alloc.h index fc28d64398c1..55762b554b99 100644 --- a/fs/ocfs2/alloc.h +++ b/fs/ocfs2/alloc.h | |||
@@ -140,8 +140,9 @@ int ocfs2_remove_extent(handle_t *handle, struct ocfs2_extent_tree *et, | |||
140 | struct ocfs2_cached_dealloc_ctxt *dealloc); | 140 | struct ocfs2_cached_dealloc_ctxt *dealloc); |
141 | int ocfs2_remove_btree_range(struct inode *inode, | 141 | int ocfs2_remove_btree_range(struct inode *inode, |
142 | struct ocfs2_extent_tree *et, | 142 | struct ocfs2_extent_tree *et, |
143 | u32 cpos, u32 phys_cpos, u32 len, | 143 | u32 cpos, u32 phys_cpos, u32 len, int flags, |
144 | struct ocfs2_cached_dealloc_ctxt *dealloc); | 144 | struct ocfs2_cached_dealloc_ctxt *dealloc, |
145 | u64 refcount_loc); | ||
145 | 146 | ||
146 | int ocfs2_num_free_extents(struct ocfs2_super *osb, | 147 | int ocfs2_num_free_extents(struct ocfs2_super *osb, |
147 | struct ocfs2_extent_tree *et); | 148 | struct ocfs2_extent_tree *et); |
@@ -233,8 +234,7 @@ int ocfs2_prepare_truncate(struct ocfs2_super *osb, | |||
233 | struct ocfs2_truncate_context **tc); | 234 | struct ocfs2_truncate_context **tc); |
234 | int ocfs2_commit_truncate(struct ocfs2_super *osb, | 235 | int ocfs2_commit_truncate(struct ocfs2_super *osb, |
235 | struct inode *inode, | 236 | struct inode *inode, |
236 | struct buffer_head *fe_bh, | 237 | struct buffer_head *di_bh); |
237 | struct ocfs2_truncate_context *tc); | ||
238 | int ocfs2_truncate_inline(struct inode *inode, struct buffer_head *di_bh, | 238 | int ocfs2_truncate_inline(struct inode *inode, struct buffer_head *di_bh, |
239 | unsigned int start, unsigned int end, int trunc); | 239 | unsigned int start, unsigned int end, int trunc); |
240 | 240 | ||
@@ -319,6 +319,8 @@ int ocfs2_journal_access_path(struct ocfs2_caching_info *ci, | |||
319 | struct ocfs2_path *path); | 319 | struct ocfs2_path *path); |
320 | int ocfs2_find_cpos_for_right_leaf(struct super_block *sb, | 320 | int ocfs2_find_cpos_for_right_leaf(struct super_block *sb, |
321 | struct ocfs2_path *path, u32 *cpos); | 321 | struct ocfs2_path *path, u32 *cpos); |
322 | int ocfs2_find_cpos_for_left_leaf(struct super_block *sb, | ||
323 | struct ocfs2_path *path, u32 *cpos); | ||
322 | int ocfs2_find_subtree_root(struct ocfs2_extent_tree *et, | 324 | int ocfs2_find_subtree_root(struct ocfs2_extent_tree *et, |
323 | struct ocfs2_path *left, | 325 | struct ocfs2_path *left, |
324 | struct ocfs2_path *right); | 326 | struct ocfs2_path *right); |
diff --git a/fs/ocfs2/dir.c b/fs/ocfs2/dir.c index 3fea52d0efd3..f04ebcfffc4a 100644 --- a/fs/ocfs2/dir.c +++ b/fs/ocfs2/dir.c | |||
@@ -4530,8 +4530,8 @@ int ocfs2_dx_dir_truncate(struct inode *dir, struct buffer_head *di_bh) | |||
4530 | 4530 | ||
4531 | p_cpos = ocfs2_blocks_to_clusters(dir->i_sb, blkno); | 4531 | p_cpos = ocfs2_blocks_to_clusters(dir->i_sb, blkno); |
4532 | 4532 | ||
4533 | ret = ocfs2_remove_btree_range(dir, &et, cpos, p_cpos, clen, | 4533 | ret = ocfs2_remove_btree_range(dir, &et, cpos, p_cpos, clen, 0, |
4534 | &dealloc); | 4534 | &dealloc, 0); |
4535 | if (ret) { | 4535 | if (ret) { |
4536 | mlog_errno(ret); | 4536 | mlog_errno(ret); |
4537 | goto out; | 4537 | goto out; |
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c index e82c0537eff9..6b5a492e1749 100644 --- a/fs/ocfs2/dlm/dlmdomain.c +++ b/fs/ocfs2/dlm/dlmdomain.c | |||
@@ -1523,7 +1523,7 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain, | |||
1523 | goto leave; | 1523 | goto leave; |
1524 | } | 1524 | } |
1525 | 1525 | ||
1526 | dlm->name = kmalloc(strlen(domain) + 1, GFP_KERNEL); | 1526 | dlm->name = kstrdup(domain, GFP_KERNEL); |
1527 | if (dlm->name == NULL) { | 1527 | if (dlm->name == NULL) { |
1528 | mlog_errno(-ENOMEM); | 1528 | mlog_errno(-ENOMEM); |
1529 | kfree(dlm); | 1529 | kfree(dlm); |
@@ -1557,7 +1557,6 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain, | |||
1557 | for (i = 0; i < DLM_HASH_BUCKETS; i++) | 1557 | for (i = 0; i < DLM_HASH_BUCKETS; i++) |
1558 | INIT_HLIST_HEAD(dlm_master_hash(dlm, i)); | 1558 | INIT_HLIST_HEAD(dlm_master_hash(dlm, i)); |
1559 | 1559 | ||
1560 | strcpy(dlm->name, domain); | ||
1561 | dlm->key = key; | 1560 | dlm->key = key; |
1562 | dlm->node_num = o2nm_this_node(); | 1561 | dlm->node_num = o2nm_this_node(); |
1563 | 1562 | ||
diff --git a/fs/ocfs2/dlm/dlmlock.c b/fs/ocfs2/dlm/dlmlock.c index f1fba2a6a8fe..69cf369961c4 100644 --- a/fs/ocfs2/dlm/dlmlock.c +++ b/fs/ocfs2/dlm/dlmlock.c | |||
@@ -431,7 +431,7 @@ struct dlm_lock * dlm_new_lock(int type, u8 node, u64 cookie, | |||
431 | struct dlm_lock *lock; | 431 | struct dlm_lock *lock; |
432 | int kernel_allocated = 0; | 432 | int kernel_allocated = 0; |
433 | 433 | ||
434 | lock = (struct dlm_lock *) kmem_cache_zalloc(dlm_lock_cache, GFP_NOFS); | 434 | lock = kmem_cache_zalloc(dlm_lock_cache, GFP_NOFS); |
435 | if (!lock) | 435 | if (!lock) |
436 | return NULL; | 436 | return NULL; |
437 | 437 | ||
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c index 3114de2e74c7..b01e34819a09 100644 --- a/fs/ocfs2/dlm/dlmmaster.c +++ b/fs/ocfs2/dlm/dlmmaster.c | |||
@@ -617,13 +617,11 @@ struct dlm_lock_resource *dlm_new_lockres(struct dlm_ctxt *dlm, | |||
617 | { | 617 | { |
618 | struct dlm_lock_resource *res = NULL; | 618 | struct dlm_lock_resource *res = NULL; |
619 | 619 | ||
620 | res = (struct dlm_lock_resource *) | 620 | res = kmem_cache_zalloc(dlm_lockres_cache, GFP_NOFS); |
621 | kmem_cache_zalloc(dlm_lockres_cache, GFP_NOFS); | ||
622 | if (!res) | 621 | if (!res) |
623 | goto error; | 622 | goto error; |
624 | 623 | ||
625 | res->lockname.name = (char *) | 624 | res->lockname.name = kmem_cache_zalloc(dlm_lockname_cache, GFP_NOFS); |
626 | kmem_cache_zalloc(dlm_lockname_cache, GFP_NOFS); | ||
627 | if (!res->lockname.name) | 625 | if (!res->lockname.name) |
628 | goto error; | 626 | goto error; |
629 | 627 | ||
@@ -757,8 +755,7 @@ lookup: | |||
757 | spin_unlock(&dlm->spinlock); | 755 | spin_unlock(&dlm->spinlock); |
758 | mlog(0, "allocating a new resource\n"); | 756 | mlog(0, "allocating a new resource\n"); |
759 | /* nothing found and we need to allocate one. */ | 757 | /* nothing found and we need to allocate one. */ |
760 | alloc_mle = (struct dlm_master_list_entry *) | 758 | alloc_mle = kmem_cache_alloc(dlm_mle_cache, GFP_NOFS); |
761 | kmem_cache_alloc(dlm_mle_cache, GFP_NOFS); | ||
762 | if (!alloc_mle) | 759 | if (!alloc_mle) |
763 | goto leave; | 760 | goto leave; |
764 | res = dlm_new_lockres(dlm, lockid, namelen); | 761 | res = dlm_new_lockres(dlm, lockid, namelen); |
@@ -1542,8 +1539,7 @@ way_up_top: | |||
1542 | spin_unlock(&dlm->master_lock); | 1539 | spin_unlock(&dlm->master_lock); |
1543 | spin_unlock(&dlm->spinlock); | 1540 | spin_unlock(&dlm->spinlock); |
1544 | 1541 | ||
1545 | mle = (struct dlm_master_list_entry *) | 1542 | mle = kmem_cache_alloc(dlm_mle_cache, GFP_NOFS); |
1546 | kmem_cache_alloc(dlm_mle_cache, GFP_NOFS); | ||
1547 | if (!mle) { | 1543 | if (!mle) { |
1548 | response = DLM_MASTER_RESP_ERROR; | 1544 | response = DLM_MASTER_RESP_ERROR; |
1549 | mlog_errno(-ENOMEM); | 1545 | mlog_errno(-ENOMEM); |
@@ -2458,8 +2454,7 @@ static int dlm_migrate_lockres(struct dlm_ctxt *dlm, | |||
2458 | goto leave; | 2454 | goto leave; |
2459 | } | 2455 | } |
2460 | 2456 | ||
2461 | mle = (struct dlm_master_list_entry *) kmem_cache_alloc(dlm_mle_cache, | 2457 | mle = kmem_cache_alloc(dlm_mle_cache, GFP_NOFS); |
2462 | GFP_NOFS); | ||
2463 | if (!mle) { | 2458 | if (!mle) { |
2464 | mlog_errno(ret); | 2459 | mlog_errno(ret); |
2465 | goto leave; | 2460 | goto leave; |
@@ -3041,8 +3036,7 @@ int dlm_migrate_request_handler(struct o2net_msg *msg, u32 len, void *data, | |||
3041 | hash = dlm_lockid_hash(name, namelen); | 3036 | hash = dlm_lockid_hash(name, namelen); |
3042 | 3037 | ||
3043 | /* preallocate.. if this fails, abort */ | 3038 | /* preallocate.. if this fails, abort */ |
3044 | mle = (struct dlm_master_list_entry *) kmem_cache_alloc(dlm_mle_cache, | 3039 | mle = kmem_cache_alloc(dlm_mle_cache, GFP_NOFS); |
3045 | GFP_NOFS); | ||
3046 | 3040 | ||
3047 | if (!mle) { | 3041 | if (!mle) { |
3048 | ret = -ENOMEM; | 3042 | ret = -ENOMEM; |
diff --git a/fs/ocfs2/file.c b/fs/ocfs2/file.c index 19d16f2ef81e..9c1047c2e44e 100644 --- a/fs/ocfs2/file.c +++ b/fs/ocfs2/file.c | |||
@@ -444,7 +444,6 @@ static int ocfs2_truncate_file(struct inode *inode, | |||
444 | int status = 0; | 444 | int status = 0; |
445 | struct ocfs2_dinode *fe = NULL; | 445 | struct ocfs2_dinode *fe = NULL; |
446 | struct ocfs2_super *osb = OCFS2_SB(inode->i_sb); | 446 | struct ocfs2_super *osb = OCFS2_SB(inode->i_sb); |
447 | struct ocfs2_truncate_context *tc = NULL; | ||
448 | 447 | ||
449 | mlog_entry("(inode = %llu, new_i_size = %llu\n", | 448 | mlog_entry("(inode = %llu, new_i_size = %llu\n", |
450 | (unsigned long long)OCFS2_I(inode)->ip_blkno, | 449 | (unsigned long long)OCFS2_I(inode)->ip_blkno, |
@@ -515,13 +514,7 @@ static int ocfs2_truncate_file(struct inode *inode, | |||
515 | goto bail_unlock_sem; | 514 | goto bail_unlock_sem; |
516 | } | 515 | } |
517 | 516 | ||
518 | status = ocfs2_prepare_truncate(osb, inode, di_bh, &tc); | 517 | status = ocfs2_commit_truncate(osb, inode, di_bh); |
519 | if (status < 0) { | ||
520 | mlog_errno(status); | ||
521 | goto bail_unlock_sem; | ||
522 | } | ||
523 | |||
524 | status = ocfs2_commit_truncate(osb, inode, di_bh, tc); | ||
525 | if (status < 0) { | 518 | if (status < 0) { |
526 | mlog_errno(status); | 519 | mlog_errno(status); |
527 | goto bail_unlock_sem; | 520 | goto bail_unlock_sem; |
@@ -1425,16 +1418,90 @@ out: | |||
1425 | return ret; | 1418 | return ret; |
1426 | } | 1419 | } |
1427 | 1420 | ||
1421 | static int ocfs2_find_rec(struct ocfs2_extent_list *el, u32 pos) | ||
1422 | { | ||
1423 | int i; | ||
1424 | struct ocfs2_extent_rec *rec = NULL; | ||
1425 | |||
1426 | for (i = le16_to_cpu(el->l_next_free_rec) - 1; i >= 0; i--) { | ||
1427 | |||
1428 | rec = &el->l_recs[i]; | ||
1429 | |||
1430 | if (le32_to_cpu(rec->e_cpos) < pos) | ||
1431 | break; | ||
1432 | } | ||
1433 | |||
1434 | return i; | ||
1435 | } | ||
1436 | |||
1437 | /* | ||
1438 | * Helper to calculate the punching pos and length in one run, we handle the | ||
1439 | * following three cases in order: | ||
1440 | * | ||
1441 | * - remove the entire record | ||
1442 | * - remove a partial record | ||
1443 | * - no record needs to be removed (hole-punching completed) | ||
1444 | */ | ||
1445 | static void ocfs2_calc_trunc_pos(struct inode *inode, | ||
1446 | struct ocfs2_extent_list *el, | ||
1447 | struct ocfs2_extent_rec *rec, | ||
1448 | u32 trunc_start, u32 *trunc_cpos, | ||
1449 | u32 *trunc_len, u32 *trunc_end, | ||
1450 | u64 *blkno, int *done) | ||
1451 | { | ||
1452 | int ret = 0; | ||
1453 | u32 coff, range; | ||
1454 | |||
1455 | range = le32_to_cpu(rec->e_cpos) + ocfs2_rec_clusters(el, rec); | ||
1456 | |||
1457 | if (le32_to_cpu(rec->e_cpos) >= trunc_start) { | ||
1458 | *trunc_cpos = le32_to_cpu(rec->e_cpos); | ||
1459 | /* | ||
1460 | * Skip holes if any. | ||
1461 | */ | ||
1462 | if (range < *trunc_end) | ||
1463 | *trunc_end = range; | ||
1464 | *trunc_len = *trunc_end - le32_to_cpu(rec->e_cpos); | ||
1465 | *blkno = le64_to_cpu(rec->e_blkno); | ||
1466 | *trunc_end = le32_to_cpu(rec->e_cpos); | ||
1467 | } else if (range > trunc_start) { | ||
1468 | *trunc_cpos = trunc_start; | ||
1469 | *trunc_len = *trunc_end - trunc_start; | ||
1470 | coff = trunc_start - le32_to_cpu(rec->e_cpos); | ||
1471 | *blkno = le64_to_cpu(rec->e_blkno) + | ||
1472 | ocfs2_clusters_to_blocks(inode->i_sb, coff); | ||
1473 | *trunc_end = trunc_start; | ||
1474 | } else { | ||
1475 | /* | ||
1476 | * It may have two following possibilities: | ||
1477 | * | ||
1478 | * - last record has been removed | ||
1479 | * - trunc_start was within a hole | ||
1480 | * | ||
1481 | * both two cases mean the completion of hole punching. | ||
1482 | */ | ||
1483 | ret = 1; | ||
1484 | } | ||
1485 | |||
1486 | *done = ret; | ||
1487 | } | ||
1488 | |||
1428 | static int ocfs2_remove_inode_range(struct inode *inode, | 1489 | static int ocfs2_remove_inode_range(struct inode *inode, |
1429 | struct buffer_head *di_bh, u64 byte_start, | 1490 | struct buffer_head *di_bh, u64 byte_start, |
1430 | u64 byte_len) | 1491 | u64 byte_len) |
1431 | { | 1492 | { |
1432 | int ret = 0; | 1493 | int ret = 0, flags = 0, done = 0, i; |
1433 | u32 trunc_start, trunc_len, cpos, phys_cpos, alloc_size; | 1494 | u32 trunc_start, trunc_len, trunc_end, trunc_cpos, phys_cpos; |
1495 | u32 cluster_in_el; | ||
1434 | struct ocfs2_super *osb = OCFS2_SB(inode->i_sb); | 1496 | struct ocfs2_super *osb = OCFS2_SB(inode->i_sb); |
1435 | struct ocfs2_cached_dealloc_ctxt dealloc; | 1497 | struct ocfs2_cached_dealloc_ctxt dealloc; |
1436 | struct address_space *mapping = inode->i_mapping; | 1498 | struct address_space *mapping = inode->i_mapping; |
1437 | struct ocfs2_extent_tree et; | 1499 | struct ocfs2_extent_tree et; |
1500 | struct ocfs2_path *path = NULL; | ||
1501 | struct ocfs2_extent_list *el = NULL; | ||
1502 | struct ocfs2_extent_rec *rec = NULL; | ||
1503 | struct ocfs2_dinode *di = (struct ocfs2_dinode *)di_bh->b_data; | ||
1504 | u64 blkno, refcount_loc = le64_to_cpu(di->i_refcount_loc); | ||
1438 | 1505 | ||
1439 | ocfs2_init_dinode_extent_tree(&et, INODE_CACHE(inode), di_bh); | 1506 | ocfs2_init_dinode_extent_tree(&et, INODE_CACHE(inode), di_bh); |
1440 | ocfs2_init_dealloc_ctxt(&dealloc); | 1507 | ocfs2_init_dealloc_ctxt(&dealloc); |
@@ -1460,17 +1527,35 @@ static int ocfs2_remove_inode_range(struct inode *inode, | |||
1460 | goto out; | 1527 | goto out; |
1461 | } | 1528 | } |
1462 | 1529 | ||
1530 | /* | ||
1531 | * For reflinks, we may need to CoW 2 clusters which might be | ||
1532 | * partially zero'd later, if hole's start and end offset were | ||
1533 | * within one cluster(means is not exactly aligned to clustersize). | ||
1534 | */ | ||
1535 | |||
1536 | if (OCFS2_I(inode)->ip_dyn_features & OCFS2_HAS_REFCOUNT_FL) { | ||
1537 | |||
1538 | ret = ocfs2_cow_file_pos(inode, di_bh, byte_start); | ||
1539 | if (ret) { | ||
1540 | mlog_errno(ret); | ||
1541 | goto out; | ||
1542 | } | ||
1543 | |||
1544 | ret = ocfs2_cow_file_pos(inode, di_bh, byte_start + byte_len); | ||
1545 | if (ret) { | ||
1546 | mlog_errno(ret); | ||
1547 | goto out; | ||
1548 | } | ||
1549 | } | ||
1550 | |||
1463 | trunc_start = ocfs2_clusters_for_bytes(osb->sb, byte_start); | 1551 | trunc_start = ocfs2_clusters_for_bytes(osb->sb, byte_start); |
1464 | trunc_len = (byte_start + byte_len) >> osb->s_clustersize_bits; | 1552 | trunc_end = (byte_start + byte_len) >> osb->s_clustersize_bits; |
1465 | if (trunc_len >= trunc_start) | 1553 | cluster_in_el = trunc_end; |
1466 | trunc_len -= trunc_start; | ||
1467 | else | ||
1468 | trunc_len = 0; | ||
1469 | 1554 | ||
1470 | mlog(0, "Inode: %llu, start: %llu, len: %llu, cstart: %u, clen: %u\n", | 1555 | mlog(0, "Inode: %llu, start: %llu, len: %llu, cstart: %u, cend: %u\n", |
1471 | (unsigned long long)OCFS2_I(inode)->ip_blkno, | 1556 | (unsigned long long)OCFS2_I(inode)->ip_blkno, |
1472 | (unsigned long long)byte_start, | 1557 | (unsigned long long)byte_start, |
1473 | (unsigned long long)byte_len, trunc_start, trunc_len); | 1558 | (unsigned long long)byte_len, trunc_start, trunc_end); |
1474 | 1559 | ||
1475 | ret = ocfs2_zero_partial_clusters(inode, byte_start, byte_len); | 1560 | ret = ocfs2_zero_partial_clusters(inode, byte_start, byte_len); |
1476 | if (ret) { | 1561 | if (ret) { |
@@ -1478,31 +1563,79 @@ static int ocfs2_remove_inode_range(struct inode *inode, | |||
1478 | goto out; | 1563 | goto out; |
1479 | } | 1564 | } |
1480 | 1565 | ||
1481 | cpos = trunc_start; | 1566 | path = ocfs2_new_path_from_et(&et); |
1482 | while (trunc_len) { | 1567 | if (!path) { |
1483 | ret = ocfs2_get_clusters(inode, cpos, &phys_cpos, | 1568 | ret = -ENOMEM; |
1484 | &alloc_size, NULL); | 1569 | mlog_errno(ret); |
1570 | goto out; | ||
1571 | } | ||
1572 | |||
1573 | while (trunc_end > trunc_start) { | ||
1574 | |||
1575 | ret = ocfs2_find_path(INODE_CACHE(inode), path, | ||
1576 | cluster_in_el); | ||
1485 | if (ret) { | 1577 | if (ret) { |
1486 | mlog_errno(ret); | 1578 | mlog_errno(ret); |
1487 | goto out; | 1579 | goto out; |
1488 | } | 1580 | } |
1489 | 1581 | ||
1490 | if (alloc_size > trunc_len) | 1582 | el = path_leaf_el(path); |
1491 | alloc_size = trunc_len; | 1583 | |
1584 | i = ocfs2_find_rec(el, trunc_end); | ||
1585 | /* | ||
1586 | * Need to go to previous extent block. | ||
1587 | */ | ||
1588 | if (i < 0) { | ||
1589 | if (path->p_tree_depth == 0) | ||
1590 | break; | ||
1492 | 1591 | ||
1493 | /* Only do work for non-holes */ | 1592 | ret = ocfs2_find_cpos_for_left_leaf(inode->i_sb, |
1494 | if (phys_cpos != 0) { | 1593 | path, |
1495 | ret = ocfs2_remove_btree_range(inode, &et, cpos, | 1594 | &cluster_in_el); |
1496 | phys_cpos, alloc_size, | ||
1497 | &dealloc); | ||
1498 | if (ret) { | 1595 | if (ret) { |
1499 | mlog_errno(ret); | 1596 | mlog_errno(ret); |
1500 | goto out; | 1597 | goto out; |
1501 | } | 1598 | } |
1599 | |||
1600 | /* | ||
1601 | * We've reached the leftmost extent block, | ||
1602 | * it's safe to leave. | ||
1603 | */ | ||
1604 | if (cluster_in_el == 0) | ||
1605 | break; | ||
1606 | |||
1607 | /* | ||
1608 | * The 'pos' searched for previous extent block is | ||
1609 | * always one cluster less than actual trunc_end. | ||
1610 | */ | ||
1611 | trunc_end = cluster_in_el + 1; | ||
1612 | |||
1613 | ocfs2_reinit_path(path, 1); | ||
1614 | |||
1615 | continue; | ||
1616 | |||
1617 | } else | ||
1618 | rec = &el->l_recs[i]; | ||
1619 | |||
1620 | ocfs2_calc_trunc_pos(inode, el, rec, trunc_start, &trunc_cpos, | ||
1621 | &trunc_len, &trunc_end, &blkno, &done); | ||
1622 | if (done) | ||
1623 | break; | ||
1624 | |||
1625 | flags = rec->e_flags; | ||
1626 | phys_cpos = ocfs2_blocks_to_clusters(inode->i_sb, blkno); | ||
1627 | |||
1628 | ret = ocfs2_remove_btree_range(inode, &et, trunc_cpos, | ||
1629 | phys_cpos, trunc_len, flags, | ||
1630 | &dealloc, refcount_loc); | ||
1631 | if (ret < 0) { | ||
1632 | mlog_errno(ret); | ||
1633 | goto out; | ||
1502 | } | 1634 | } |
1503 | 1635 | ||
1504 | cpos += alloc_size; | 1636 | cluster_in_el = trunc_end; |
1505 | trunc_len -= alloc_size; | 1637 | |
1638 | ocfs2_reinit_path(path, 1); | ||
1506 | } | 1639 | } |
1507 | 1640 | ||
1508 | ocfs2_truncate_cluster_pages(inode, byte_start, byte_len); | 1641 | ocfs2_truncate_cluster_pages(inode, byte_start, byte_len); |
diff --git a/fs/ocfs2/inode.c b/fs/ocfs2/inode.c index 9ee13f70da57..9a17251f3d9e 100644 --- a/fs/ocfs2/inode.c +++ b/fs/ocfs2/inode.c | |||
@@ -544,7 +544,6 @@ static int ocfs2_truncate_for_delete(struct ocfs2_super *osb, | |||
544 | struct buffer_head *fe_bh) | 544 | struct buffer_head *fe_bh) |
545 | { | 545 | { |
546 | int status = 0; | 546 | int status = 0; |
547 | struct ocfs2_truncate_context *tc = NULL; | ||
548 | struct ocfs2_dinode *fe; | 547 | struct ocfs2_dinode *fe; |
549 | handle_t *handle = NULL; | 548 | handle_t *handle = NULL; |
550 | 549 | ||
@@ -586,13 +585,7 @@ static int ocfs2_truncate_for_delete(struct ocfs2_super *osb, | |||
586 | ocfs2_commit_trans(osb, handle); | 585 | ocfs2_commit_trans(osb, handle); |
587 | handle = NULL; | 586 | handle = NULL; |
588 | 587 | ||
589 | status = ocfs2_prepare_truncate(osb, inode, fe_bh, &tc); | 588 | status = ocfs2_commit_truncate(osb, inode, fe_bh); |
590 | if (status < 0) { | ||
591 | mlog_errno(status); | ||
592 | goto out; | ||
593 | } | ||
594 | |||
595 | status = ocfs2_commit_truncate(osb, inode, fe_bh, tc); | ||
596 | if (status < 0) { | 589 | if (status < 0) { |
597 | mlog_errno(status); | 590 | mlog_errno(status); |
598 | goto out; | 591 | goto out; |
@@ -957,7 +950,7 @@ static void ocfs2_cleanup_delete_inode(struct inode *inode, | |||
957 | void ocfs2_delete_inode(struct inode *inode) | 950 | void ocfs2_delete_inode(struct inode *inode) |
958 | { | 951 | { |
959 | int wipe, status; | 952 | int wipe, status; |
960 | sigset_t blocked, oldset; | 953 | sigset_t oldset; |
961 | struct buffer_head *di_bh = NULL; | 954 | struct buffer_head *di_bh = NULL; |
962 | 955 | ||
963 | mlog_entry("(inode->i_ino = %lu)\n", inode->i_ino); | 956 | mlog_entry("(inode->i_ino = %lu)\n", inode->i_ino); |
@@ -984,13 +977,7 @@ void ocfs2_delete_inode(struct inode *inode) | |||
984 | * messaging paths may return us -ERESTARTSYS. Which would | 977 | * messaging paths may return us -ERESTARTSYS. Which would |
985 | * cause us to exit early, resulting in inodes being orphaned | 978 | * cause us to exit early, resulting in inodes being orphaned |
986 | * forever. */ | 979 | * forever. */ |
987 | sigfillset(&blocked); | 980 | ocfs2_block_signals(&oldset); |
988 | status = sigprocmask(SIG_BLOCK, &blocked, &oldset); | ||
989 | if (status < 0) { | ||
990 | mlog_errno(status); | ||
991 | ocfs2_cleanup_delete_inode(inode, 1); | ||
992 | goto bail; | ||
993 | } | ||
994 | 981 | ||
995 | /* | 982 | /* |
996 | * Synchronize us against ocfs2_get_dentry. We take this in | 983 | * Synchronize us against ocfs2_get_dentry. We take this in |
@@ -1064,9 +1051,7 @@ bail_unlock_nfs_sync: | |||
1064 | ocfs2_nfs_sync_unlock(OCFS2_SB(inode->i_sb), 0); | 1051 | ocfs2_nfs_sync_unlock(OCFS2_SB(inode->i_sb), 0); |
1065 | 1052 | ||
1066 | bail_unblock: | 1053 | bail_unblock: |
1067 | status = sigprocmask(SIG_SETMASK, &oldset, NULL); | 1054 | ocfs2_unblock_signals(&oldset); |
1068 | if (status < 0) | ||
1069 | mlog_errno(status); | ||
1070 | bail: | 1055 | bail: |
1071 | clear_inode(inode); | 1056 | clear_inode(inode); |
1072 | mlog_exit_void(); | 1057 | mlog_exit_void(); |
diff --git a/fs/ocfs2/mmap.c b/fs/ocfs2/mmap.c index 39737613424a..a61809f8eab5 100644 --- a/fs/ocfs2/mmap.c +++ b/fs/ocfs2/mmap.c | |||
@@ -42,44 +42,20 @@ | |||
42 | #include "file.h" | 42 | #include "file.h" |
43 | #include "inode.h" | 43 | #include "inode.h" |
44 | #include "mmap.h" | 44 | #include "mmap.h" |
45 | #include "super.h" | ||
45 | 46 | ||
46 | static inline int ocfs2_vm_op_block_sigs(sigset_t *blocked, sigset_t *oldset) | ||
47 | { | ||
48 | /* The best way to deal with signals in the vm path is | ||
49 | * to block them upfront, rather than allowing the | ||
50 | * locking paths to return -ERESTARTSYS. */ | ||
51 | sigfillset(blocked); | ||
52 | |||
53 | /* We should technically never get a bad return value | ||
54 | * from sigprocmask */ | ||
55 | return sigprocmask(SIG_BLOCK, blocked, oldset); | ||
56 | } | ||
57 | |||
58 | static inline int ocfs2_vm_op_unblock_sigs(sigset_t *oldset) | ||
59 | { | ||
60 | return sigprocmask(SIG_SETMASK, oldset, NULL); | ||
61 | } | ||
62 | 47 | ||
63 | static int ocfs2_fault(struct vm_area_struct *area, struct vm_fault *vmf) | 48 | static int ocfs2_fault(struct vm_area_struct *area, struct vm_fault *vmf) |
64 | { | 49 | { |
65 | sigset_t blocked, oldset; | 50 | sigset_t oldset; |
66 | int error, ret; | 51 | int ret; |
67 | 52 | ||
68 | mlog_entry("(area=%p, page offset=%lu)\n", area, vmf->pgoff); | 53 | mlog_entry("(area=%p, page offset=%lu)\n", area, vmf->pgoff); |
69 | 54 | ||
70 | error = ocfs2_vm_op_block_sigs(&blocked, &oldset); | 55 | ocfs2_block_signals(&oldset); |
71 | if (error < 0) { | ||
72 | mlog_errno(error); | ||
73 | ret = VM_FAULT_SIGBUS; | ||
74 | goto out; | ||
75 | } | ||
76 | |||
77 | ret = filemap_fault(area, vmf); | 56 | ret = filemap_fault(area, vmf); |
57 | ocfs2_unblock_signals(&oldset); | ||
78 | 58 | ||
79 | error = ocfs2_vm_op_unblock_sigs(&oldset); | ||
80 | if (error < 0) | ||
81 | mlog_errno(error); | ||
82 | out: | ||
83 | mlog_exit_ptr(vmf->page); | 59 | mlog_exit_ptr(vmf->page); |
84 | return ret; | 60 | return ret; |
85 | } | 61 | } |
@@ -159,14 +135,10 @@ static int ocfs2_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) | |||
159 | struct page *page = vmf->page; | 135 | struct page *page = vmf->page; |
160 | struct inode *inode = vma->vm_file->f_path.dentry->d_inode; | 136 | struct inode *inode = vma->vm_file->f_path.dentry->d_inode; |
161 | struct buffer_head *di_bh = NULL; | 137 | struct buffer_head *di_bh = NULL; |
162 | sigset_t blocked, oldset; | 138 | sigset_t oldset; |
163 | int ret, ret2; | 139 | int ret; |
164 | 140 | ||
165 | ret = ocfs2_vm_op_block_sigs(&blocked, &oldset); | 141 | ocfs2_block_signals(&oldset); |
166 | if (ret < 0) { | ||
167 | mlog_errno(ret); | ||
168 | return ret; | ||
169 | } | ||
170 | 142 | ||
171 | /* | 143 | /* |
172 | * The cluster locks taken will block a truncate from another | 144 | * The cluster locks taken will block a truncate from another |
@@ -194,9 +166,7 @@ static int ocfs2_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) | |||
194 | ocfs2_inode_unlock(inode, 1); | 166 | ocfs2_inode_unlock(inode, 1); |
195 | 167 | ||
196 | out: | 168 | out: |
197 | ret2 = ocfs2_vm_op_unblock_sigs(&oldset); | 169 | ocfs2_unblock_signals(&oldset); |
198 | if (ret2 < 0) | ||
199 | mlog_errno(ret2); | ||
200 | if (ret) | 170 | if (ret) |
201 | ret = VM_FAULT_SIGBUS; | 171 | ret = VM_FAULT_SIGBUS; |
202 | return ret; | 172 | return ret; |
diff --git a/fs/ocfs2/namei.c b/fs/ocfs2/namei.c index bfe4571a4fa1..b0fa6b650751 100644 --- a/fs/ocfs2/namei.c +++ b/fs/ocfs2/namei.c | |||
@@ -239,6 +239,8 @@ static int ocfs2_mknod(struct inode *dir, | |||
239 | }; | 239 | }; |
240 | int did_quota_inode = 0; | 240 | int did_quota_inode = 0; |
241 | struct ocfs2_dir_lookup_result lookup = { NULL, }; | 241 | struct ocfs2_dir_lookup_result lookup = { NULL, }; |
242 | sigset_t oldset; | ||
243 | int did_block_signals = 0; | ||
242 | 244 | ||
243 | mlog_entry("(0x%p, 0x%p, %d, %lu, '%.*s')\n", dir, dentry, mode, | 245 | mlog_entry("(0x%p, 0x%p, %d, %lu, '%.*s')\n", dir, dentry, mode, |
244 | (unsigned long)dev, dentry->d_name.len, | 246 | (unsigned long)dev, dentry->d_name.len, |
@@ -350,6 +352,10 @@ static int ocfs2_mknod(struct inode *dir, | |||
350 | goto leave; | 352 | goto leave; |
351 | } | 353 | } |
352 | 354 | ||
355 | /* Starting to change things, restart is no longer possible. */ | ||
356 | ocfs2_block_signals(&oldset); | ||
357 | did_block_signals = 1; | ||
358 | |||
353 | status = dquot_alloc_inode(inode); | 359 | status = dquot_alloc_inode(inode); |
354 | if (status) | 360 | if (status) |
355 | goto leave; | 361 | goto leave; |
@@ -430,6 +436,8 @@ leave: | |||
430 | ocfs2_commit_trans(osb, handle); | 436 | ocfs2_commit_trans(osb, handle); |
431 | 437 | ||
432 | ocfs2_inode_unlock(dir, 1); | 438 | ocfs2_inode_unlock(dir, 1); |
439 | if (did_block_signals) | ||
440 | ocfs2_unblock_signals(&oldset); | ||
433 | 441 | ||
434 | if (status == -ENOSPC) | 442 | if (status == -ENOSPC) |
435 | mlog(0, "Disk is full\n"); | 443 | mlog(0, "Disk is full\n"); |
@@ -620,6 +628,7 @@ static int ocfs2_link(struct dentry *old_dentry, | |||
620 | struct ocfs2_dinode *fe = NULL; | 628 | struct ocfs2_dinode *fe = NULL; |
621 | struct ocfs2_super *osb = OCFS2_SB(dir->i_sb); | 629 | struct ocfs2_super *osb = OCFS2_SB(dir->i_sb); |
622 | struct ocfs2_dir_lookup_result lookup = { NULL, }; | 630 | struct ocfs2_dir_lookup_result lookup = { NULL, }; |
631 | sigset_t oldset; | ||
623 | 632 | ||
624 | mlog_entry("(inode=%lu, old='%.*s' new='%.*s')\n", inode->i_ino, | 633 | mlog_entry("(inode=%lu, old='%.*s' new='%.*s')\n", inode->i_ino, |
625 | old_dentry->d_name.len, old_dentry->d_name.name, | 634 | old_dentry->d_name.len, old_dentry->d_name.name, |
@@ -676,6 +685,9 @@ static int ocfs2_link(struct dentry *old_dentry, | |||
676 | goto out_unlock_inode; | 685 | goto out_unlock_inode; |
677 | } | 686 | } |
678 | 687 | ||
688 | /* Starting to change things, restart is no longer possible. */ | ||
689 | ocfs2_block_signals(&oldset); | ||
690 | |||
679 | err = ocfs2_journal_access_di(handle, INODE_CACHE(inode), fe_bh, | 691 | err = ocfs2_journal_access_di(handle, INODE_CACHE(inode), fe_bh, |
680 | OCFS2_JOURNAL_ACCESS_WRITE); | 692 | OCFS2_JOURNAL_ACCESS_WRITE); |
681 | if (err < 0) { | 693 | if (err < 0) { |
@@ -712,6 +724,7 @@ static int ocfs2_link(struct dentry *old_dentry, | |||
712 | 724 | ||
713 | out_commit: | 725 | out_commit: |
714 | ocfs2_commit_trans(osb, handle); | 726 | ocfs2_commit_trans(osb, handle); |
727 | ocfs2_unblock_signals(&oldset); | ||
715 | out_unlock_inode: | 728 | out_unlock_inode: |
716 | ocfs2_inode_unlock(inode, 1); | 729 | ocfs2_inode_unlock(inode, 1); |
717 | 730 | ||
@@ -1570,6 +1583,8 @@ static int ocfs2_symlink(struct inode *dir, | |||
1570 | }; | 1583 | }; |
1571 | int did_quota = 0, did_quota_inode = 0; | 1584 | int did_quota = 0, did_quota_inode = 0; |
1572 | struct ocfs2_dir_lookup_result lookup = { NULL, }; | 1585 | struct ocfs2_dir_lookup_result lookup = { NULL, }; |
1586 | sigset_t oldset; | ||
1587 | int did_block_signals = 0; | ||
1573 | 1588 | ||
1574 | mlog_entry("(0x%p, 0x%p, symname='%s' actual='%.*s')\n", dir, | 1589 | mlog_entry("(0x%p, 0x%p, symname='%s' actual='%.*s')\n", dir, |
1575 | dentry, symname, dentry->d_name.len, dentry->d_name.name); | 1590 | dentry, symname, dentry->d_name.len, dentry->d_name.name); |
@@ -1665,6 +1680,10 @@ static int ocfs2_symlink(struct inode *dir, | |||
1665 | goto bail; | 1680 | goto bail; |
1666 | } | 1681 | } |
1667 | 1682 | ||
1683 | /* Starting to change things, restart is no longer possible. */ | ||
1684 | ocfs2_block_signals(&oldset); | ||
1685 | did_block_signals = 1; | ||
1686 | |||
1668 | status = dquot_alloc_inode(inode); | 1687 | status = dquot_alloc_inode(inode); |
1669 | if (status) | 1688 | if (status) |
1670 | goto bail; | 1689 | goto bail; |
@@ -1768,6 +1787,8 @@ bail: | |||
1768 | ocfs2_commit_trans(osb, handle); | 1787 | ocfs2_commit_trans(osb, handle); |
1769 | 1788 | ||
1770 | ocfs2_inode_unlock(dir, 1); | 1789 | ocfs2_inode_unlock(dir, 1); |
1790 | if (did_block_signals) | ||
1791 | ocfs2_unblock_signals(&oldset); | ||
1771 | 1792 | ||
1772 | brelse(new_fe_bh); | 1793 | brelse(new_fe_bh); |
1773 | brelse(parent_fe_bh); | 1794 | brelse(parent_fe_bh); |
diff --git a/fs/ocfs2/refcounttree.c b/fs/ocfs2/refcounttree.c index b34702984225..52e4f6ee1e23 100644 --- a/fs/ocfs2/refcounttree.c +++ b/fs/ocfs2/refcounttree.c | |||
@@ -2516,20 +2516,19 @@ out: | |||
2516 | * | 2516 | * |
2517 | * Normally the refcount blocks store these refcount should be | 2517 | * Normally the refcount blocks store these refcount should be |
2518 | * contiguous also, so that we can get the number easily. | 2518 | * contiguous also, so that we can get the number easily. |
2519 | * As for meta_ac, we will at most add split 2 refcount record and | 2519 | * We will at most add split 2 refcount records and 2 more |
2520 | * 2 more refcount block, so just check it in a rough way. | 2520 | * refcount blocks, so just check it in a rough way. |
2521 | * | 2521 | * |
2522 | * Caller must hold refcount tree lock. | 2522 | * Caller must hold refcount tree lock. |
2523 | */ | 2523 | */ |
2524 | int ocfs2_prepare_refcount_change_for_del(struct inode *inode, | 2524 | int ocfs2_prepare_refcount_change_for_del(struct inode *inode, |
2525 | struct buffer_head *di_bh, | 2525 | u64 refcount_loc, |
2526 | u64 phys_blkno, | 2526 | u64 phys_blkno, |
2527 | u32 clusters, | 2527 | u32 clusters, |
2528 | int *credits, | 2528 | int *credits, |
2529 | struct ocfs2_alloc_context **meta_ac) | 2529 | int *ref_blocks) |
2530 | { | 2530 | { |
2531 | int ret, ref_blocks = 0; | 2531 | int ret; |
2532 | struct ocfs2_dinode *di = (struct ocfs2_dinode *)di_bh->b_data; | ||
2533 | struct ocfs2_inode_info *oi = OCFS2_I(inode); | 2532 | struct ocfs2_inode_info *oi = OCFS2_I(inode); |
2534 | struct buffer_head *ref_root_bh = NULL; | 2533 | struct buffer_head *ref_root_bh = NULL; |
2535 | struct ocfs2_refcount_tree *tree; | 2534 | struct ocfs2_refcount_tree *tree; |
@@ -2546,14 +2545,13 @@ int ocfs2_prepare_refcount_change_for_del(struct inode *inode, | |||
2546 | BUG_ON(!(oi->ip_dyn_features & OCFS2_HAS_REFCOUNT_FL)); | 2545 | BUG_ON(!(oi->ip_dyn_features & OCFS2_HAS_REFCOUNT_FL)); |
2547 | 2546 | ||
2548 | ret = ocfs2_get_refcount_tree(OCFS2_SB(inode->i_sb), | 2547 | ret = ocfs2_get_refcount_tree(OCFS2_SB(inode->i_sb), |
2549 | le64_to_cpu(di->i_refcount_loc), &tree); | 2548 | refcount_loc, &tree); |
2550 | if (ret) { | 2549 | if (ret) { |
2551 | mlog_errno(ret); | 2550 | mlog_errno(ret); |
2552 | goto out; | 2551 | goto out; |
2553 | } | 2552 | } |
2554 | 2553 | ||
2555 | ret = ocfs2_read_refcount_block(&tree->rf_ci, | 2554 | ret = ocfs2_read_refcount_block(&tree->rf_ci, refcount_loc, |
2556 | le64_to_cpu(di->i_refcount_loc), | ||
2557 | &ref_root_bh); | 2555 | &ref_root_bh); |
2558 | if (ret) { | 2556 | if (ret) { |
2559 | mlog_errno(ret); | 2557 | mlog_errno(ret); |
@@ -2564,21 +2562,14 @@ int ocfs2_prepare_refcount_change_for_del(struct inode *inode, | |||
2564 | &tree->rf_ci, | 2562 | &tree->rf_ci, |
2565 | ref_root_bh, | 2563 | ref_root_bh, |
2566 | start_cpos, clusters, | 2564 | start_cpos, clusters, |
2567 | &ref_blocks, credits); | 2565 | ref_blocks, credits); |
2568 | if (ret) { | 2566 | if (ret) { |
2569 | mlog_errno(ret); | 2567 | mlog_errno(ret); |
2570 | goto out; | 2568 | goto out; |
2571 | } | 2569 | } |
2572 | 2570 | ||
2573 | mlog(0, "reserve new metadata %d, credits = %d\n", | 2571 | mlog(0, "reserve new metadata %d blocks, credits = %d\n", |
2574 | ref_blocks, *credits); | 2572 | *ref_blocks, *credits); |
2575 | |||
2576 | if (ref_blocks) { | ||
2577 | ret = ocfs2_reserve_new_metadata_blocks(OCFS2_SB(inode->i_sb), | ||
2578 | ref_blocks, meta_ac); | ||
2579 | if (ret) | ||
2580 | mlog_errno(ret); | ||
2581 | } | ||
2582 | 2573 | ||
2583 | out: | 2574 | out: |
2584 | brelse(ref_root_bh); | 2575 | brelse(ref_root_bh); |
diff --git a/fs/ocfs2/refcounttree.h b/fs/ocfs2/refcounttree.h index c1d19b1d3ecc..9983ba1570e2 100644 --- a/fs/ocfs2/refcounttree.h +++ b/fs/ocfs2/refcounttree.h | |||
@@ -47,11 +47,11 @@ int ocfs2_decrease_refcount(struct inode *inode, | |||
47 | struct ocfs2_cached_dealloc_ctxt *dealloc, | 47 | struct ocfs2_cached_dealloc_ctxt *dealloc, |
48 | int delete); | 48 | int delete); |
49 | int ocfs2_prepare_refcount_change_for_del(struct inode *inode, | 49 | int ocfs2_prepare_refcount_change_for_del(struct inode *inode, |
50 | struct buffer_head *di_bh, | 50 | u64 refcount_loc, |
51 | u64 phys_blkno, | 51 | u64 phys_blkno, |
52 | u32 clusters, | 52 | u32 clusters, |
53 | int *credits, | 53 | int *credits, |
54 | struct ocfs2_alloc_context **meta_ac); | 54 | int *ref_blocks); |
55 | int ocfs2_refcount_cow(struct inode *inode, struct buffer_head *di_bh, | 55 | int ocfs2_refcount_cow(struct inode *inode, struct buffer_head *di_bh, |
56 | u32 cpos, u32 write_len, u32 max_cpos); | 56 | u32 cpos, u32 write_len, u32 max_cpos); |
57 | 57 | ||
diff --git a/fs/ocfs2/super.c b/fs/ocfs2/super.c index 106becf5d00f..1c2c39f6f0b6 100644 --- a/fs/ocfs2/super.c +++ b/fs/ocfs2/super.c | |||
@@ -2561,5 +2561,25 @@ void __ocfs2_abort(struct super_block* sb, | |||
2561 | ocfs2_handle_error(sb); | 2561 | ocfs2_handle_error(sb); |
2562 | } | 2562 | } |
2563 | 2563 | ||
2564 | /* | ||
2565 | * Void signal blockers, because in-kernel sigprocmask() only fails | ||
2566 | * when SIG_* is wrong. | ||
2567 | */ | ||
2568 | void ocfs2_block_signals(sigset_t *oldset) | ||
2569 | { | ||
2570 | int rc; | ||
2571 | sigset_t blocked; | ||
2572 | |||
2573 | sigfillset(&blocked); | ||
2574 | rc = sigprocmask(SIG_BLOCK, &blocked, oldset); | ||
2575 | BUG_ON(rc); | ||
2576 | } | ||
2577 | |||
2578 | void ocfs2_unblock_signals(sigset_t *oldset) | ||
2579 | { | ||
2580 | int rc = sigprocmask(SIG_SETMASK, oldset, NULL); | ||
2581 | BUG_ON(rc); | ||
2582 | } | ||
2583 | |||
2564 | module_init(ocfs2_init); | 2584 | module_init(ocfs2_init); |
2565 | module_exit(ocfs2_exit); | 2585 | module_exit(ocfs2_exit); |
diff --git a/fs/ocfs2/super.h b/fs/ocfs2/super.h index 783f5270f2a1..40c7de084c10 100644 --- a/fs/ocfs2/super.h +++ b/fs/ocfs2/super.h | |||
@@ -45,4 +45,11 @@ void __ocfs2_abort(struct super_block *sb, | |||
45 | 45 | ||
46 | #define ocfs2_abort(sb, fmt, args...) __ocfs2_abort(sb, __PRETTY_FUNCTION__, fmt, ##args) | 46 | #define ocfs2_abort(sb, fmt, args...) __ocfs2_abort(sb, __PRETTY_FUNCTION__, fmt, ##args) |
47 | 47 | ||
48 | /* | ||
49 | * Void signal blockers, because in-kernel sigprocmask() only fails | ||
50 | * when SIG_* is wrong. | ||
51 | */ | ||
52 | void ocfs2_block_signals(sigset_t *oldset); | ||
53 | void ocfs2_unblock_signals(sigset_t *oldset); | ||
54 | |||
48 | #endif /* OCFS2_SUPER_H */ | 55 | #endif /* OCFS2_SUPER_H */ |