| 22 | |
| 23 | |
| 24 | NTSTATUS |
| 25 | Ext2MapExtent( |
| 26 | IN PEXT2_IRP_CONTEXT IrpContext, |
| 27 | IN PEXT2_VCB Vcb, |
| 28 | IN PEXT2_MCB Mcb, |
| 29 | IN ULONG Index, |
| 30 | IN BOOLEAN Alloc, |
| 31 | OUT PULONG Block, |
| 32 | OUT PULONG Number |
| 33 | ) |
| 34 | { |
| 35 | EXT4_EXTENT_HEADER *eh; |
| 36 | struct buffer_head bh_got = {0}; |
| 37 | int flags, rc; |
| 38 | ULONG max_blocks = 0; |
| 39 | |
| 40 | memset(&bh_got, 0, sizeof(struct buffer_head)); |
| 41 | eh = get_ext4_header(&Mcb->Inode); |
| 42 | |
| 43 | if (eh->eh_magic != EXT4_EXT_MAGIC) { |
| 44 | if (Alloc) { |
| 45 | /* now initialize inode extent root node */ |
| 46 | ext4_ext_tree_init(IrpContext, NULL, &Mcb->Inode); |
| 47 | } else { |
| 48 | /* return empty-mapping when inode extent isn't initialized */ |
| 49 | if (Block) |
| 50 | *Block = 0; |
| 51 | if (Number) { |
| 52 | LONGLONG _len = _len = Mcb->Inode.i_size; |
| 53 | if (Mcb->Fcb) |
| 54 | _len = Mcb->Fcb->Header.AllocationSize.QuadPart; |
| 55 | *Number = (ULONG)((_len + BLOCK_SIZE - 1) >> BLOCK_BITS); |
| 56 | } |
| 57 | return STATUS_SUCCESS; |
| 58 | } |
| 59 | } |
| 60 | |
| 61 | /* IrpContext is NULL when called during journal initialization */ |
| 62 | if (IsMcbDirectory(Mcb) || IrpContext == NULL || |
| 63 | IrpContext->MajorFunction == IRP_MJ_WRITE || !Alloc){ |
| 64 | flags = EXT4_GET_BLOCKS_IO_CONVERT_EXT; |
| 65 | max_blocks = EXT_INIT_MAX_LEN; |
| 66 | } else { |
| 67 | flags = EXT4_GET_BLOCKS_IO_CREATE_EXT; |
| 68 | max_blocks = EXT_UNWRITTEN_MAX_LEN; |
| 69 | } |
| 70 | |
| 71 | if (Alloc) { |
| 72 | if (Number && !*Number) { |
| 73 | if (max_blocks > *Number) { |
| 74 | max_blocks = *Number; |
| 75 | } |
| 76 | } else { |
| 77 | max_blocks = 1; |
| 78 | } |
| 79 | } |
| 80 | |
| 81 | if ((rc = ext4_ext_get_blocks( |
no test coverage detected