* ext4_ext_insert_index: * insert new index [@logical;@ptr] into the block at @curp; * check where to insert: before @curp or after @curp */
| 700 | * check where to insert: before @curp or after @curp |
| 701 | */ |
| 702 | static int ext4_ext_insert_index(void *icb, handle_t *handle, struct inode *inode, |
| 703 | struct ext4_ext_path *curp, |
| 704 | int logical, ext4_fsblk_t ptr) |
| 705 | { |
| 706 | struct ext4_extent_idx *ix; |
| 707 | int len, err; |
| 708 | |
| 709 | err = ext4_ext_get_access(icb, handle, inode, curp); |
| 710 | if (err) |
| 711 | return err; |
| 712 | |
| 713 | if (unlikely(logical == le32_to_cpu(curp->p_idx->ei_block))) { |
| 714 | EXT4_ERROR_INODE(inode, |
| 715 | "logical %d == ei_block %d!", |
| 716 | logical, le32_to_cpu(curp->p_idx->ei_block)); |
| 717 | return -EIO; |
| 718 | } |
| 719 | |
| 720 | if (unlikely(le16_to_cpu(curp->p_hdr->eh_entries) |
| 721 | >= le16_to_cpu(curp->p_hdr->eh_max))) { |
| 722 | EXT4_ERROR_INODE(inode, |
| 723 | "eh_entries %d >= eh_max %d!", |
| 724 | le16_to_cpu(curp->p_hdr->eh_entries), |
| 725 | le16_to_cpu(curp->p_hdr->eh_max)); |
| 726 | return -EIO; |
| 727 | } |
| 728 | |
| 729 | if (logical > le32_to_cpu(curp->p_idx->ei_block)) { |
| 730 | /* insert after */ |
| 731 | ext_debug("insert new index %d after: %llu\n", logical, ptr); |
| 732 | ix = curp->p_idx + 1; |
| 733 | } else { |
| 734 | /* insert before */ |
| 735 | ext_debug("insert new index %d before: %llu\n", logical, ptr); |
| 736 | ix = curp->p_idx; |
| 737 | } |
| 738 | |
| 739 | len = EXT_LAST_INDEX(curp->p_hdr) - ix + 1; |
| 740 | BUG_ON(len < 0); |
| 741 | if (len > 0) { |
| 742 | ext_debug("insert new index %d: " |
| 743 | "move %d indices from 0x%p to 0x%p\n", |
| 744 | logical, len, ix, ix + 1); |
| 745 | memmove(ix + 1, ix, len * sizeof(struct ext4_extent_idx)); |
| 746 | } |
| 747 | |
| 748 | if (unlikely(ix > EXT_MAX_INDEX(curp->p_hdr))) { |
| 749 | EXT4_ERROR_INODE(inode, "ix > EXT_MAX_INDEX!"); |
| 750 | return -EIO; |
| 751 | } |
| 752 | |
| 753 | ix->ei_block = cpu_to_le32(logical); |
| 754 | ext4_idx_store_pblock(ix, ptr); |
| 755 | le16_add_cpu(&curp->p_hdr->eh_entries, 1); |
| 756 | |
| 757 | if (unlikely(ix > EXT_LAST_INDEX(curp->p_hdr))) { |
| 758 | EXT4_ERROR_INODE(inode, "ix > EXT_LAST_INDEX!"); |
| 759 | return -EIO; |
no test coverage detected