inode.c (14b393ee768e8339b9c64f82df24e8c081bdbff9) | inode.c (6fed42bb7750e217b0d1169ccfccc7639a3e1d3f) |
---|---|
1// SPDX-License-Identifier: GPL-2.0 2 3#include "bcachefs.h" 4#include "btree_key_cache.h" 5#include "bkey_methods.h" 6#include "btree_update.h" 7#include "error.h" 8#include "extents.h" | 1// SPDX-License-Identifier: GPL-2.0 2 3#include "bcachefs.h" 4#include "btree_key_cache.h" 5#include "bkey_methods.h" 6#include "btree_update.h" 7#include "error.h" 8#include "extents.h" |
9#include "extent_update.h" |
|
9#include "inode.h" 10#include "str_hash.h" 11#include "subvolume.h" 12#include "varint.h" 13 14#include <linux/random.h> 15 16#include <asm/unaligned.h> --- 274 unchanged lines hidden (view full) --- 291 } 292 293 return 0; 294} 295 296int bch2_inode_peek(struct btree_trans *trans, 297 struct btree_iter *iter, 298 struct bch_inode_unpacked *inode, | 10#include "inode.h" 11#include "str_hash.h" 12#include "subvolume.h" 13#include "varint.h" 14 15#include <linux/random.h> 16 17#include <asm/unaligned.h> --- 274 unchanged lines hidden (view full) --- 292 } 293 294 return 0; 295} 296 297int bch2_inode_peek(struct btree_trans *trans, 298 struct btree_iter *iter, 299 struct bch_inode_unpacked *inode, |
299 u64 inum, unsigned flags) | 300 subvol_inum inum, unsigned flags) |
300{ 301 struct bkey_s_c k; | 301{ 302 struct bkey_s_c k; |
303 u32 snapshot; |
|
302 int ret; 303 304 if (trans->c->opts.inodes_use_key_cache) 305 flags |= BTREE_ITER_CACHED; 306 | 304 int ret; 305 306 if (trans->c->opts.inodes_use_key_cache) 307 flags |= BTREE_ITER_CACHED; 308 |
307 bch2_trans_iter_init(trans, iter, BTREE_ID_inodes, POS(0, inum), flags); | 309 ret = bch2_subvolume_get_snapshot(trans, inum.subvol, &snapshot); 310 if (ret) 311 return ret; 312 313 bch2_trans_iter_init(trans, iter, BTREE_ID_inodes, 314 SPOS(0, inum.inum, snapshot), flags); |
308 k = bch2_btree_iter_peek_slot(iter); 309 ret = bkey_err(k); 310 if (ret) 311 goto err; 312 313 ret = k.k->type == KEY_TYPE_inode ? 0 : -ENOENT; 314 if (ret) 315 goto err; --- 165 unchanged lines hidden (view full) --- 481 BUG(); 482 case KEY_TYPE_inode_generation: 483 return le32_to_cpu(bkey_s_c_to_inode_generation(k).v->bi_generation); 484 default: 485 return 0; 486 } 487} 488 | 315 k = bch2_btree_iter_peek_slot(iter); 316 ret = bkey_err(k); 317 if (ret) 318 goto err; 319 320 ret = k.k->type == KEY_TYPE_inode ? 0 : -ENOENT; 321 if (ret) 322 goto err; --- 165 unchanged lines hidden (view full) --- 488 BUG(); 489 case KEY_TYPE_inode_generation: 490 return le32_to_cpu(bkey_s_c_to_inode_generation(k).v->bi_generation); 491 default: 492 return 0; 493 } 494} 495 |
496/* 497 * This just finds an empty slot: 498 */ |
|
489int bch2_inode_create(struct btree_trans *trans, 490 struct btree_iter *iter, 491 struct bch_inode_unpacked *inode_u, 492 u32 snapshot, u64 cpu) 493{ 494 struct bch_fs *c = trans->c; 495 struct bkey_s_c k; 496 u64 min, max, start, pos, *hint; --- 83 unchanged lines hidden (view full) --- 580 goto again; 581 582 *hint = k.k->p.offset; 583 inode_u->bi_inum = k.k->p.offset; 584 inode_u->bi_generation = bkey_generation(k); 585 return 0; 586} 587 | 499int bch2_inode_create(struct btree_trans *trans, 500 struct btree_iter *iter, 501 struct bch_inode_unpacked *inode_u, 502 u32 snapshot, u64 cpu) 503{ 504 struct bch_fs *c = trans->c; 505 struct bkey_s_c k; 506 u64 min, max, start, pos, *hint; --- 83 unchanged lines hidden (view full) --- 590 goto again; 591 592 *hint = k.k->p.offset; 593 inode_u->bi_inum = k.k->p.offset; 594 inode_u->bi_generation = bkey_generation(k); 595 return 0; 596} 597 |
588int bch2_inode_rm(struct bch_fs *c, u64 inode_nr, bool cached) | 598static int bch2_inode_delete_keys(struct btree_trans *trans, 599 subvol_inum inum, enum btree_id id) |
589{ | 600{ |
601 u64 offset = 0; 602 int ret = 0; 603 604 while (!ret || ret == -EINTR) { 605 struct btree_iter iter; 606 struct bkey_s_c k; 607 struct bkey_i delete; 608 u32 snapshot; 609 610 bch2_trans_begin(trans); 611 612 ret = bch2_subvolume_get_snapshot(trans, inum.subvol, &snapshot); 613 if (ret) 614 continue; 615 616 bch2_trans_iter_init(trans, &iter, id, 617 SPOS(inum.inum, offset, snapshot), 618 BTREE_ITER_INTENT); 619 k = bch2_btree_iter_peek(&iter); 620 621 if (!k.k || iter.pos.inode != inum.inum) { 622 bch2_trans_iter_exit(trans, &iter); 623 break; 624 } 625 626 ret = bkey_err(k); 627 if (ret) 628 goto err; 629 630 bkey_init(&delete.k); 631 delete.k.p = iter.pos; 632 633 if (btree_node_type_is_extents(iter.btree_id)) { 634 unsigned max_sectors = 635 min_t(u64, U64_MAX - iter.pos.offset, 636 KEY_SIZE_MAX & (~0 << trans->c->block_bits)); 637 638 /* create the biggest key we can */ 639 bch2_key_resize(&delete.k, max_sectors); 640 641 ret = bch2_extent_trim_atomic(trans, &iter, &delete); 642 if (ret) 643 goto err; 644 } 645 646 ret = bch2_trans_update(trans, &iter, &delete, 0) ?: 647 bch2_trans_commit(trans, NULL, NULL, 648 BTREE_INSERT_NOFAIL); 649err: 650 offset = iter.pos.offset; 651 bch2_trans_iter_exit(trans, &iter); 652 } 653 654 return ret; 655} 656 657int bch2_inode_rm(struct bch_fs *c, subvol_inum inum, bool cached) 658{ |
|
590 struct btree_trans trans; 591 struct btree_iter iter = { NULL }; 592 struct bkey_i_inode_generation delete; | 659 struct btree_trans trans; 660 struct btree_iter iter = { NULL }; 661 struct bkey_i_inode_generation delete; |
593 struct bpos start = POS(inode_nr, 0); 594 struct bpos end = POS(inode_nr + 1, 0); | |
595 struct bch_inode_unpacked inode_u; 596 struct bkey_s_c k; 597 unsigned iter_flags = BTREE_ITER_INTENT; | 662 struct bch_inode_unpacked inode_u; 663 struct bkey_s_c k; 664 unsigned iter_flags = BTREE_ITER_INTENT; |
665 u32 snapshot; |
|
598 int ret; 599 600 if (cached && c->opts.inodes_use_key_cache) 601 iter_flags |= BTREE_ITER_CACHED; 602 603 bch2_trans_init(&trans, c, 0, 1024); 604 605 /* 606 * If this was a directory, there shouldn't be any real dirents left - 607 * but there could be whiteouts (from hash collisions) that we should 608 * delete: 609 * 610 * XXX: the dirent could ideally would delete whiteouts when they're no 611 * longer needed 612 */ | 666 int ret; 667 668 if (cached && c->opts.inodes_use_key_cache) 669 iter_flags |= BTREE_ITER_CACHED; 670 671 bch2_trans_init(&trans, c, 0, 1024); 672 673 /* 674 * If this was a directory, there shouldn't be any real dirents left - 675 * but there could be whiteouts (from hash collisions) that we should 676 * delete: 677 * 678 * XXX: the dirent could ideally would delete whiteouts when they're no 679 * longer needed 680 */ |
613 ret = bch2_btree_delete_range_trans(&trans, BTREE_ID_extents, 614 start, end, NULL) ?: 615 bch2_btree_delete_range_trans(&trans, BTREE_ID_xattrs, 616 start, end, NULL) ?: 617 bch2_btree_delete_range_trans(&trans, BTREE_ID_dirents, 618 start, end, NULL); | 681 ret = bch2_inode_delete_keys(&trans, inum, BTREE_ID_extents) ?: 682 bch2_inode_delete_keys(&trans, inum, BTREE_ID_xattrs) ?: 683 bch2_inode_delete_keys(&trans, inum, BTREE_ID_dirents); |
619 if (ret) 620 goto err; 621retry: 622 bch2_trans_begin(&trans); 623 | 684 if (ret) 685 goto err; 686retry: 687 bch2_trans_begin(&trans); 688 |
689 ret = bch2_subvolume_get_snapshot(&trans, inum.subvol, &snapshot); 690 if (ret) 691 goto err; 692 |
|
624 bch2_trans_iter_init(&trans, &iter, BTREE_ID_inodes, | 693 bch2_trans_iter_init(&trans, &iter, BTREE_ID_inodes, |
625 POS(0, inode_nr), iter_flags); | 694 SPOS(0, inum.inum, snapshot), iter_flags); |
626 k = bch2_btree_iter_peek_slot(&iter); 627 628 ret = bkey_err(k); 629 if (ret) 630 goto err; 631 632 if (k.k->type != KEY_TYPE_inode) { 633 bch2_fs_inconsistent(trans.c, 634 "inode %llu not found when deleting", | 695 k = bch2_btree_iter_peek_slot(&iter); 696 697 ret = bkey_err(k); 698 if (ret) 699 goto err; 700 701 if (k.k->type != KEY_TYPE_inode) { 702 bch2_fs_inconsistent(trans.c, 703 "inode %llu not found when deleting", |
635 inode_nr); | 704 inum.inum); |
636 ret = -EIO; 637 goto err; 638 } 639 640 bch2_inode_unpack(bkey_s_c_to_inode(k), &inode_u); 641 642 /* Subvolume root? */ 643 if (inode_u.bi_subvol) { --- 13 unchanged lines hidden (view full) --- 657 bch2_trans_iter_exit(&trans, &iter); 658 if (ret == -EINTR) 659 goto retry; 660 661 bch2_trans_exit(&trans); 662 return ret; 663} 664 | 705 ret = -EIO; 706 goto err; 707 } 708 709 bch2_inode_unpack(bkey_s_c_to_inode(k), &inode_u); 710 711 /* Subvolume root? */ 712 if (inode_u.bi_subvol) { --- 13 unchanged lines hidden (view full) --- 726 bch2_trans_iter_exit(&trans, &iter); 727 if (ret == -EINTR) 728 goto retry; 729 730 bch2_trans_exit(&trans); 731 return ret; 732} 733 |
665static int bch2_inode_find_by_inum_trans(struct btree_trans *trans, u64 inode_nr, | 734static int bch2_inode_find_by_inum_trans(struct btree_trans *trans, 735 subvol_inum inum, |
666 struct bch_inode_unpacked *inode) 667{ | 736 struct bch_inode_unpacked *inode) 737{ |
668 struct btree_iter iter = { NULL }; | 738 struct btree_iter iter; |
669 int ret; 670 | 739 int ret; 740 |
671 ret = bch2_inode_peek(trans, &iter, inode, inode_nr, 0); 672 bch2_trans_iter_exit(trans, &iter); | 741 ret = bch2_inode_peek(trans, &iter, inode, inum, 0); 742 if (!ret) 743 bch2_trans_iter_exit(trans, &iter); |
673 return ret; 674} 675 | 744 return ret; 745} 746 |
676int bch2_inode_find_by_inum(struct bch_fs *c, u64 inode_nr, | 747int bch2_inode_find_by_inum(struct bch_fs *c, subvol_inum inum, |
677 struct bch_inode_unpacked *inode) 678{ 679 return bch2_trans_do(c, NULL, NULL, 0, | 748 struct bch_inode_unpacked *inode) 749{ 750 return bch2_trans_do(c, NULL, NULL, 0, |
680 bch2_inode_find_by_inum_trans(&trans, inode_nr, inode)); | 751 bch2_inode_find_by_inum_trans(&trans, inum, inode)); |
681} | 752} |