diff options
Diffstat (limited to 'fs/btrfs/file-item.c')
-rw-r--r-- | fs/btrfs/file-item.c | 75 |
1 files changed, 74 insertions, 1 deletions
diff --git a/fs/btrfs/file-item.c b/fs/btrfs/file-item.c index 6dbe88b9d7d4..f4d3fa71bc41 100644 --- a/fs/btrfs/file-item.c +++ b/fs/btrfs/file-item.c | |||
@@ -31,7 +31,8 @@ int btrfs_insert_file_extent(struct btrfs_trans_handle *trans, | |||
31 | struct btrfs_root *root, | 31 | struct btrfs_root *root, |
32 | u64 objectid, u64 pos, | 32 | u64 objectid, u64 pos, |
33 | u64 disk_offset, u64 disk_num_bytes, | 33 | u64 disk_offset, u64 disk_num_bytes, |
34 | u64 num_bytes, u64 offset) | 34 | u64 num_bytes, u64 offset, u64 ram_bytes, |
35 | u8 compression, u8 encryption, u16 other_encoding) | ||
35 | { | 36 | { |
36 | int ret = 0; | 37 | int ret = 0; |
37 | struct btrfs_file_extent_item *item; | 38 | struct btrfs_file_extent_item *item; |
@@ -57,8 +58,13 @@ int btrfs_insert_file_extent(struct btrfs_trans_handle *trans, | |||
57 | btrfs_set_file_extent_disk_num_bytes(leaf, item, disk_num_bytes); | 58 | btrfs_set_file_extent_disk_num_bytes(leaf, item, disk_num_bytes); |
58 | btrfs_set_file_extent_offset(leaf, item, offset); | 59 | btrfs_set_file_extent_offset(leaf, item, offset); |
59 | btrfs_set_file_extent_num_bytes(leaf, item, num_bytes); | 60 | btrfs_set_file_extent_num_bytes(leaf, item, num_bytes); |
61 | btrfs_set_file_extent_ram_bytes(leaf, item, ram_bytes); | ||
60 | btrfs_set_file_extent_generation(leaf, item, trans->transid); | 62 | btrfs_set_file_extent_generation(leaf, item, trans->transid); |
61 | btrfs_set_file_extent_type(leaf, item, BTRFS_FILE_EXTENT_REG); | 63 | btrfs_set_file_extent_type(leaf, item, BTRFS_FILE_EXTENT_REG); |
64 | btrfs_set_file_extent_compression(leaf, item, compression); | ||
65 | btrfs_set_file_extent_encryption(leaf, item, encryption); | ||
66 | btrfs_set_file_extent_other_encoding(leaf, item, other_encoding); | ||
67 | |||
62 | btrfs_mark_buffer_dirty(leaf); | 68 | btrfs_mark_buffer_dirty(leaf); |
63 | out: | 69 | out: |
64 | btrfs_free_path(path); | 70 | btrfs_free_path(path); |
@@ -213,6 +219,73 @@ found: | |||
213 | return 0; | 219 | return 0; |
214 | } | 220 | } |
215 | 221 | ||
222 | int btrfs_csum_file_bytes(struct btrfs_root *root, struct inode *inode, | ||
223 | u64 start, unsigned long len) | ||
224 | { | ||
225 | struct btrfs_ordered_sum *sums; | ||
226 | struct btrfs_sector_sum *sector_sum; | ||
227 | struct btrfs_ordered_extent *ordered; | ||
228 | char *data; | ||
229 | struct page *page; | ||
230 | unsigned long total_bytes = 0; | ||
231 | unsigned long this_sum_bytes = 0; | ||
232 | |||
233 | sums = kzalloc(btrfs_ordered_sum_size(root, len), GFP_NOFS); | ||
234 | if (!sums) | ||
235 | return -ENOMEM; | ||
236 | |||
237 | sector_sum = sums->sums; | ||
238 | sums->file_offset = start; | ||
239 | sums->len = len; | ||
240 | INIT_LIST_HEAD(&sums->list); | ||
241 | ordered = btrfs_lookup_ordered_extent(inode, sums->file_offset); | ||
242 | BUG_ON(!ordered); | ||
243 | |||
244 | while(len > 0) { | ||
245 | if (start >= ordered->file_offset + ordered->len || | ||
246 | start < ordered->file_offset) { | ||
247 | sums->len = this_sum_bytes; | ||
248 | this_sum_bytes = 0; | ||
249 | btrfs_add_ordered_sum(inode, ordered, sums); | ||
250 | btrfs_put_ordered_extent(ordered); | ||
251 | |||
252 | sums = kzalloc(btrfs_ordered_sum_size(root, len), | ||
253 | GFP_NOFS); | ||
254 | BUG_ON(!sums); | ||
255 | sector_sum = sums->sums; | ||
256 | sums->len = len; | ||
257 | sums->file_offset = start; | ||
258 | ordered = btrfs_lookup_ordered_extent(inode, | ||
259 | sums->file_offset); | ||
260 | BUG_ON(!ordered); | ||
261 | } | ||
262 | |||
263 | page = find_get_page(inode->i_mapping, | ||
264 | start >> PAGE_CACHE_SHIFT); | ||
265 | |||
266 | data = kmap_atomic(page, KM_USER0); | ||
267 | sector_sum->sum = ~(u32)0; | ||
268 | sector_sum->sum = btrfs_csum_data(root, data, sector_sum->sum, | ||
269 | PAGE_CACHE_SIZE); | ||
270 | kunmap_atomic(data, KM_USER0); | ||
271 | btrfs_csum_final(sector_sum->sum, | ||
272 | (char *)§or_sum->sum); | ||
273 | sector_sum->offset = page_offset(page); | ||
274 | page_cache_release(page); | ||
275 | |||
276 | sector_sum++; | ||
277 | total_bytes += PAGE_CACHE_SIZE; | ||
278 | this_sum_bytes += PAGE_CACHE_SIZE; | ||
279 | start += PAGE_CACHE_SIZE; | ||
280 | |||
281 | WARN_ON(len < PAGE_CACHE_SIZE); | ||
282 | len -= PAGE_CACHE_SIZE; | ||
283 | } | ||
284 | btrfs_add_ordered_sum(inode, ordered, sums); | ||
285 | btrfs_put_ordered_extent(ordered); | ||
286 | return 0; | ||
287 | } | ||
288 | |||
216 | int btrfs_csum_one_bio(struct btrfs_root *root, struct inode *inode, | 289 | int btrfs_csum_one_bio(struct btrfs_root *root, struct inode *inode, |
217 | struct bio *bio) | 290 | struct bio *bio) |
218 | { | 291 | { |