@@ -529,16 +529,14 @@ __xfs_inobt_rec_merge(
529529}
530530
531531/*
532- * Insert a new sparse inode chunk into the associated inode btree. The inode
533- * record for the sparse chunk is pre-aligned to a startino that should match
534- * any pre-existing sparse inode record in the tree. This allows sparse chunks
535- * to fill over time.
532+ * Insert a new sparse inode chunk into the associated inode allocation btree.
533+ * The inode record for the sparse chunk is pre-aligned to a startino that
534+ * should match any pre-existing sparse inode record in the tree. This allows
535+ * sparse chunks to fill over time.
536536 *
537- * This function supports two modes of handling preexisting records depending on
538- * the merge flag. If merge is true , the provided record is merged with the
537+ * If no preexisting record exists, the provided record is inserted.
538+ * If there is a preexisting record , the provided record is merged with the
539539 * existing record and updated in place. The merged record is returned in nrec.
540- * If merge is false, an existing record is replaced with the provided record.
541- * If no preexisting record exists, the provided record is always inserted.
542540 *
543541 * It is considered corruption if a merge is requested and not possible. Given
544542 * the sparse inode alignment constraints, this should never happen.
@@ -548,17 +546,15 @@ xfs_inobt_insert_sprec(
548546 struct xfs_perag * pag ,
549547 struct xfs_trans * tp ,
550548 struct xfs_buf * agbp ,
551- int btnum ,
552- struct xfs_inobt_rec_incore * nrec , /* in/out: new/merged rec. */
553- bool merge ) /* merge or replace */
549+ struct xfs_inobt_rec_incore * nrec ) /* in/out: new/merged rec. */
554550{
555551 struct xfs_mount * mp = pag -> pag_mount ;
556552 struct xfs_btree_cur * cur ;
557553 int error ;
558554 int i ;
559555 struct xfs_inobt_rec_incore rec ;
560556
561- cur = xfs_inobt_init_cursor (pag , tp , agbp , btnum );
557+ cur = xfs_inobt_init_cursor (pag , tp , agbp , XFS_BTNUM_INO );
562558
563559 /* the new record is pre-aligned so we know where to look */
564560 error = xfs_inobt_lookup (cur , nrec -> ir_startino , XFS_LOOKUP_EQ , & i );
@@ -581,48 +577,45 @@ xfs_inobt_insert_sprec(
581577 }
582578
583579 /*
584- * A record exists at this startino. Merge or replace the record
585- * depending on what we've been asked to do.
580+ * A record exists at this startino. Merge the records.
586581 */
587- if (merge ) {
588- error = xfs_inobt_get_rec (cur , & rec , & i );
589- if (error )
590- goto error ;
591- if (XFS_IS_CORRUPT (mp , i != 1 )) {
592- xfs_btree_mark_sick (cur );
593- error = - EFSCORRUPTED ;
594- goto error ;
595- }
596- if (XFS_IS_CORRUPT (mp , rec .ir_startino != nrec -> ir_startino )) {
597- xfs_btree_mark_sick (cur );
598- error = - EFSCORRUPTED ;
599- goto error ;
600- }
582+ error = xfs_inobt_get_rec (cur , & rec , & i );
583+ if (error )
584+ goto error ;
585+ if (XFS_IS_CORRUPT (mp , i != 1 )) {
586+ xfs_btree_mark_sick (cur );
587+ error = - EFSCORRUPTED ;
588+ goto error ;
589+ }
590+ if (XFS_IS_CORRUPT (mp , rec .ir_startino != nrec -> ir_startino )) {
591+ xfs_btree_mark_sick (cur );
592+ error = - EFSCORRUPTED ;
593+ goto error ;
594+ }
601595
602- /*
603- * This should never fail. If we have coexisting records that
604- * cannot merge, something is seriously wrong.
605- */
606- if (XFS_IS_CORRUPT (mp , !__xfs_inobt_can_merge (nrec , & rec ))) {
607- xfs_btree_mark_sick (cur );
608- error = - EFSCORRUPTED ;
609- goto error ;
610- }
596+ /*
597+ * This should never fail. If we have coexisting records that
598+ * cannot merge, something is seriously wrong.
599+ */
600+ if (XFS_IS_CORRUPT (mp , !__xfs_inobt_can_merge (nrec , & rec ))) {
601+ xfs_btree_mark_sick (cur );
602+ error = - EFSCORRUPTED ;
603+ goto error ;
604+ }
611605
612- trace_xfs_irec_merge_pre (mp , pag -> pag_agno , rec .ir_startino ,
613- rec .ir_holemask , nrec -> ir_startino ,
614- nrec -> ir_holemask );
606+ trace_xfs_irec_merge_pre (mp , pag -> pag_agno , rec .ir_startino ,
607+ rec .ir_holemask , nrec -> ir_startino ,
608+ nrec -> ir_holemask );
615609
616- /* merge to nrec to output the updated record */
617- __xfs_inobt_rec_merge (nrec , & rec );
610+ /* merge to nrec to output the updated record */
611+ __xfs_inobt_rec_merge (nrec , & rec );
618612
619- trace_xfs_irec_merge_post (mp , pag -> pag_agno , nrec -> ir_startino ,
620- nrec -> ir_holemask );
613+ trace_xfs_irec_merge_post (mp , pag -> pag_agno , nrec -> ir_startino ,
614+ nrec -> ir_holemask );
621615
622- error = xfs_inobt_rec_check_count (mp , nrec );
623- if (error )
624- goto error ;
625- }
616+ error = xfs_inobt_rec_check_count (mp , nrec );
617+ if (error )
618+ goto error ;
626619
627620 error = xfs_inobt_update (cur , nrec );
628621 if (error )
@@ -636,6 +629,59 @@ xfs_inobt_insert_sprec(
636629 return error ;
637630}
638631
632+ /*
633+ * Insert a new sparse inode chunk into the free inode btree. The inode
634+ * record for the sparse chunk is pre-aligned to a startino that should match
635+ * any pre-existing sparse inode record in the tree. This allows sparse chunks
636+ * to fill over time.
637+ *
638+ * The new record is always inserted, overwriting a pre-existing record if
639+ * there is one.
640+ */
641+ STATIC int
642+ xfs_finobt_insert_sprec (
643+ struct xfs_perag * pag ,
644+ struct xfs_trans * tp ,
645+ struct xfs_buf * agbp ,
646+ struct xfs_inobt_rec_incore * nrec ) /* in/out: new rec. */
647+ {
648+ struct xfs_mount * mp = pag -> pag_mount ;
649+ struct xfs_btree_cur * cur ;
650+ int error ;
651+ int i ;
652+
653+ cur = xfs_inobt_init_cursor (pag , tp , agbp , XFS_BTNUM_FINO );
654+
655+ /* the new record is pre-aligned so we know where to look */
656+ error = xfs_inobt_lookup (cur , nrec -> ir_startino , XFS_LOOKUP_EQ , & i );
657+ if (error )
658+ goto error ;
659+ /* if nothing there, insert a new record and return */
660+ if (i == 0 ) {
661+ error = xfs_inobt_insert_rec (cur , nrec -> ir_holemask ,
662+ nrec -> ir_count , nrec -> ir_freecount ,
663+ nrec -> ir_free , & i );
664+ if (error )
665+ goto error ;
666+ if (XFS_IS_CORRUPT (mp , i != 1 )) {
667+ xfs_btree_mark_sick (cur );
668+ error = - EFSCORRUPTED ;
669+ goto error ;
670+ }
671+ } else {
672+ error = xfs_inobt_update (cur , nrec );
673+ if (error )
674+ goto error ;
675+ }
676+
677+ xfs_btree_del_cursor (cur , XFS_BTREE_NOERROR );
678+ return 0 ;
679+ error :
680+ xfs_btree_del_cursor (cur , XFS_BTREE_ERROR );
681+ return error ;
682+ }
683+
684+
639685/*
640686 * Allocate new inodes in the allocation group specified by agbp. Returns 0 if
641687 * inodes were allocated in this AG; -EAGAIN if there was no space in this AG so
@@ -862,8 +908,7 @@ xfs_ialloc_ag_alloc(
862908 * if necessary. If a merge does occur, rec is updated to the
863909 * merged record.
864910 */
865- error = xfs_inobt_insert_sprec (pag , tp , agbp ,
866- XFS_BTNUM_INO , & rec , true);
911+ error = xfs_inobt_insert_sprec (pag , tp , agbp , & rec );
867912 if (error == - EFSCORRUPTED ) {
868913 xfs_alert (args .mp ,
869914 "invalid sparse inode record: ino 0x%llx holemask 0x%x count %u" ,
@@ -887,8 +932,7 @@ xfs_ialloc_ag_alloc(
887932 * existing record with this one.
888933 */
889934 if (xfs_has_finobt (args .mp )) {
890- error = xfs_inobt_insert_sprec (pag , tp , agbp ,
891- XFS_BTNUM_FINO , & rec , false);
935+ error = xfs_finobt_insert_sprec (pag , tp , agbp , & rec );
892936 if (error )
893937 return error ;
894938 }
0 commit comments