aboutsummaryrefslogtreecommitdiffstats
path: root/fs/xfs/xfs_dir2_block.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/xfs/xfs_dir2_block.c')
-rw-r--r--fs/xfs/xfs_dir2_block.c63
1 files changed, 23 insertions, 40 deletions
diff --git a/fs/xfs/xfs_dir2_block.c b/fs/xfs/xfs_dir2_block.c
index e4df1aaae2a2..f6b919af7b82 100644
--- a/fs/xfs/xfs_dir2_block.c
+++ b/fs/xfs/xfs_dir2_block.c
@@ -432,12 +432,10 @@ xfs_dir2_block_addname(
432 */ 432 */
433int /* error */ 433int /* error */
434xfs_dir2_block_getdents( 434xfs_dir2_block_getdents(
435 xfs_trans_t *tp, /* transaction (NULL) */
436 xfs_inode_t *dp, /* incore inode */ 435 xfs_inode_t *dp, /* incore inode */
437 uio_t *uio, /* caller's buffer control */ 436 void *dirent,
438 int *eofp, /* eof reached? (out) */ 437 xfs_off_t *offset,
439 xfs_dirent_t *dbp, /* caller's buffer */ 438 filldir_t filldir)
440 xfs_dir2_put_t put) /* abi's formatting function */
441{ 439{
442 xfs_dir2_block_t *block; /* directory block structure */ 440 xfs_dir2_block_t *block; /* directory block structure */
443 xfs_dabuf_t *bp; /* buffer for block */ 441 xfs_dabuf_t *bp; /* buffer for block */
@@ -447,31 +445,32 @@ xfs_dir2_block_getdents(
447 char *endptr; /* end of the data entries */ 445 char *endptr; /* end of the data entries */
448 int error; /* error return value */ 446 int error; /* error return value */
449 xfs_mount_t *mp; /* filesystem mount point */ 447 xfs_mount_t *mp; /* filesystem mount point */
450 xfs_dir2_put_args_t p; /* arg package for put rtn */
451 char *ptr; /* current data entry */ 448 char *ptr; /* current data entry */
452 int wantoff; /* starting block offset */ 449 int wantoff; /* starting block offset */
450 xfs_ino_t ino;
451 xfs_off_t cook;
453 452
454 mp = dp->i_mount; 453 mp = dp->i_mount;
455 /* 454 /*
456 * If the block number in the offset is out of range, we're done. 455 * If the block number in the offset is out of range, we're done.
457 */ 456 */
458 if (xfs_dir2_dataptr_to_db(mp, uio->uio_offset) > mp->m_dirdatablk) { 457 if (xfs_dir2_dataptr_to_db(mp, *offset) > mp->m_dirdatablk) {
459 *eofp = 1;
460 return 0; 458 return 0;
461 } 459 }
462 /* 460 /*
463 * Can't read the block, give up, else get dabuf in bp. 461 * Can't read the block, give up, else get dabuf in bp.
464 */ 462 */
465 if ((error = 463 error = xfs_da_read_buf(NULL, dp, mp->m_dirdatablk, -1,
466 xfs_da_read_buf(tp, dp, mp->m_dirdatablk, -1, &bp, XFS_DATA_FORK))) { 464 &bp, XFS_DATA_FORK);
465 if (error)
467 return error; 466 return error;
468 } 467
469 ASSERT(bp != NULL); 468 ASSERT(bp != NULL);
470 /* 469 /*
471 * Extract the byte offset we start at from the seek pointer. 470 * Extract the byte offset we start at from the seek pointer.
472 * We'll skip entries before this. 471 * We'll skip entries before this.
473 */ 472 */
474 wantoff = xfs_dir2_dataptr_to_off(mp, uio->uio_offset); 473 wantoff = xfs_dir2_dataptr_to_off(mp, *offset);
475 block = bp->data; 474 block = bp->data;
476 xfs_dir2_data_check(dp, bp); 475 xfs_dir2_data_check(dp, bp);
477 /* 476 /*
@@ -480,9 +479,7 @@ xfs_dir2_block_getdents(
480 btp = xfs_dir2_block_tail_p(mp, block); 479 btp = xfs_dir2_block_tail_p(mp, block);
481 ptr = (char *)block->u; 480 ptr = (char *)block->u;
482 endptr = (char *)xfs_dir2_block_leaf_p(btp); 481 endptr = (char *)xfs_dir2_block_leaf_p(btp);
483 p.dbp = dbp; 482
484 p.put = put;
485 p.uio = uio;
486 /* 483 /*
487 * Loop over the data portion of the block. 484 * Loop over the data portion of the block.
488 * Each object is a real entry (dep) or an unused one (dup). 485 * Each object is a real entry (dep) or an unused one (dup).
@@ -508,33 +505,24 @@ xfs_dir2_block_getdents(
508 */ 505 */
509 if ((char *)dep - (char *)block < wantoff) 506 if ((char *)dep - (char *)block < wantoff)
510 continue; 507 continue;
511 /*
512 * Set up argument structure for put routine.
513 */
514 p.namelen = dep->namelen;
515 508
516 p.cook = xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk, 509 cook = xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk,
517 ptr - (char *)block); 510 ptr - (char *)block);
518 p.ino = be64_to_cpu(dep->inumber); 511 ino = be64_to_cpu(dep->inumber);
519#if XFS_BIG_INUMS 512#if XFS_BIG_INUMS
520 p.ino += mp->m_inoadd; 513 ino += mp->m_inoadd;
521#endif 514#endif
522 p.name = (char *)dep->name;
523
524 /*
525 * Put the entry in the caller's buffer.
526 */
527 error = p.put(&p);
528 515
529 /* 516 /*
530 * If it didn't fit, set the final offset to here & return. 517 * If it didn't fit, set the final offset to here & return.
531 */ 518 */
532 if (!p.done) { 519 if (filldir(dirent, dep->name, dep->namelen, cook,
533 uio->uio_offset = 520 ino, DT_UNKNOWN)) {
534 xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk, 521 *offset = xfs_dir2_db_off_to_dataptr(mp,
522 mp->m_dirdatablk,
535 (char *)dep - (char *)block); 523 (char *)dep - (char *)block);
536 xfs_da_brelse(tp, bp); 524 xfs_da_brelse(NULL, bp);
537 return error; 525 return 0;
538 } 526 }
539 } 527 }
540 528
@@ -542,13 +530,8 @@ xfs_dir2_block_getdents(
542 * Reached the end of the block. 530 * Reached the end of the block.
543 * Set the offset to a non-existent block 1 and return. 531 * Set the offset to a non-existent block 1 and return.
544 */ 532 */
545 *eofp = 1; 533 *offset = xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk + 1, 0);
546 534 xfs_da_brelse(NULL, bp);
547 uio->uio_offset =
548 xfs_dir2_db_off_to_dataptr(mp, mp->m_dirdatablk + 1, 0);
549
550 xfs_da_brelse(tp, bp);
551
552 return 0; 535 return 0;
553} 536}
554 537