mirror of
				git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
				synced 2025-09-18 22:14:16 +00:00 
			
		
		
		
	[XFS] rewrite xfs_iflush_all
SGI-PV: 936890 SGI-Modid: xfs-linux:xfs-kern:193349a Signed-off-by: Christoph Hellwig <hch@sgi.com> Signed-off-by: Nathan Scott <nathans@sgi.com>
This commit is contained in:
		
							parent
							
								
									ba0f32d460
								
							
						
					
					
						commit
						efa8027804
					
				
					 3 changed files with 27 additions and 96 deletions
				
			
		|  | @ -3556,106 +3556,42 @@ corrupt_out: | |||
| 
 | ||||
| 
 | ||||
| /*
 | ||||
|  * Flush all inactive inodes in mp.  Return true if no user references | ||||
|  * were found, false otherwise. | ||||
|  * Flush all inactive inodes in mp. | ||||
|  */ | ||||
| int | ||||
| void | ||||
| xfs_iflush_all( | ||||
| 	xfs_mount_t	*mp, | ||||
| 	int		flag) | ||||
| 	xfs_mount_t	*mp) | ||||
| { | ||||
| 	int		busy; | ||||
| 	int		done; | ||||
| 	int		purged; | ||||
| 	xfs_inode_t	*ip; | ||||
| 	vmap_t		vmap; | ||||
| 	vnode_t		*vp; | ||||
| 
 | ||||
| 	busy = done = 0; | ||||
| 	while (!done) { | ||||
| 		purged = 0; | ||||
| 		XFS_MOUNT_ILOCK(mp); | ||||
| 		ip = mp->m_inodes; | ||||
| 		if (ip == NULL) { | ||||
| 			break; | ||||
|  again: | ||||
| 	XFS_MOUNT_ILOCK(mp); | ||||
| 	ip = mp->m_inodes; | ||||
| 	if (ip == NULL) | ||||
| 		goto out; | ||||
| 
 | ||||
| 	do { | ||||
| 		/* Make sure we skip markers inserted by sync */ | ||||
| 		if (ip->i_mount == NULL) { | ||||
| 			ip = ip->i_mnext; | ||||
| 			continue; | ||||
| 		} | ||||
| 		do { | ||||
| 			/* Make sure we skip markers inserted by sync */ | ||||
| 			if (ip->i_mount == NULL) { | ||||
| 				ip = ip->i_mnext; | ||||
| 				continue; | ||||
| 			} | ||||
| 
 | ||||
| 			/*
 | ||||
| 			 * It's up to our caller to purge the root | ||||
| 			 * and quota vnodes later. | ||||
| 			 */ | ||||
| 			vp = XFS_ITOV_NULL(ip); | ||||
| 
 | ||||
| 			if (!vp) { | ||||
| 				XFS_MOUNT_IUNLOCK(mp); | ||||
| 				xfs_finish_reclaim(ip, 0, XFS_IFLUSH_ASYNC); | ||||
| 				purged = 1; | ||||
| 				break; | ||||
| 			} | ||||
| 
 | ||||
| 			if (vn_count(vp) != 0) { | ||||
| 				if (vn_count(vp) == 1 && | ||||
| 				    (ip == mp->m_rootip || | ||||
| 				     (mp->m_quotainfo && | ||||
| 				      (ip->i_ino == mp->m_sb.sb_uquotino || | ||||
| 				       ip->i_ino == mp->m_sb.sb_gquotino)))) { | ||||
| 
 | ||||
| 					ip = ip->i_mnext; | ||||
| 					continue; | ||||
| 				} | ||||
| 				if (!(flag & XFS_FLUSH_ALL)) { | ||||
| 					busy = 1; | ||||
| 					done = 1; | ||||
| 					break; | ||||
| 				} | ||||
| 				/*
 | ||||
| 				 * Ignore busy inodes but continue flushing | ||||
| 				 * others. | ||||
| 				 */ | ||||
| 				ip = ip->i_mnext; | ||||
| 				continue; | ||||
| 			} | ||||
| 			/*
 | ||||
| 			 * Sample vp mapping while holding mp locked on MP | ||||
| 			 * systems, so we don't purge a reclaimed or | ||||
| 			 * nonexistent vnode.  We break from the loop | ||||
| 			 * since we know that we modify | ||||
| 			 * it by pulling ourselves from it in xfs_reclaim() | ||||
| 			 * called via vn_purge() below.  Set ip to the next | ||||
| 			 * entry in the list anyway so we'll know below | ||||
| 			 * whether we reached the end or not. | ||||
| 			 */ | ||||
| 			VMAP(vp, vmap); | ||||
| 		vp = XFS_ITOV_NULL(ip); | ||||
| 		if (!vp) { | ||||
| 			XFS_MOUNT_IUNLOCK(mp); | ||||
| 
 | ||||
| 			vn_purge(vp, &vmap); | ||||
| 
 | ||||
| 			purged = 1; | ||||
| 			break; | ||||
| 		} while (ip != mp->m_inodes); | ||||
| 		/*
 | ||||
| 		 * We need to distinguish between when we exit the loop | ||||
| 		 * after a purge and when we simply hit the end of the | ||||
| 		 * list.  We can't use the (ip == mp->m_inodes) test, | ||||
| 		 * because when we purge an inode at the start of the list | ||||
| 		 * the next inode on the list becomes mp->m_inodes.  That | ||||
| 		 * would cause such a test to bail out early.  The purged | ||||
| 		 * variable tells us how we got out of the loop. | ||||
| 		 */ | ||||
| 		if (!purged) { | ||||
| 			done = 1; | ||||
| 			xfs_finish_reclaim(ip, 0, XFS_IFLUSH_ASYNC); | ||||
| 			goto again; | ||||
| 		} | ||||
| 	} | ||||
| 	XFS_MOUNT_IUNLOCK(mp); | ||||
| 	return !busy; | ||||
| } | ||||
| 
 | ||||
| 		ASSERT(vn_count(vp) == 0); | ||||
| 
 | ||||
| 		ip = ip->i_mnext; | ||||
| 	} while (ip != mp->m_inodes); | ||||
|  out: | ||||
| 	XFS_MOUNT_IUNLOCK(mp); | ||||
| } | ||||
| 
 | ||||
| /*
 | ||||
|  * xfs_iaccess: check accessibility of inode for mode. | ||||
|  |  | |||
|  | @ -411,11 +411,6 @@ void xfs_ifork_next_set(xfs_inode_t *ip, int w, int n); | |||
| #define	XFS_IFLUSH_ASYNC		4 | ||||
| #define	XFS_IFLUSH_DELWRI		5 | ||||
| 
 | ||||
| /*
 | ||||
|  * Flags for xfs_iflush_all. | ||||
|  */ | ||||
| #define	XFS_FLUSH_ALL		0x1 | ||||
| 
 | ||||
| /*
 | ||||
|  * Flags for xfs_itruncate_start(). | ||||
|  */ | ||||
|  | @ -520,7 +515,7 @@ void		xfs_ipin(xfs_inode_t *); | |||
| void		xfs_iunpin(xfs_inode_t *); | ||||
| int		xfs_iextents_copy(xfs_inode_t *, xfs_bmbt_rec_t *, int); | ||||
| int		xfs_iflush(xfs_inode_t *, uint); | ||||
| int		xfs_iflush_all(struct xfs_mount *, int); | ||||
| void		xfs_iflush_all(struct xfs_mount *); | ||||
| int		xfs_iaccess(xfs_inode_t *, mode_t, cred_t *); | ||||
| uint		xfs_iroundup(uint); | ||||
| void		xfs_ichgtime(xfs_inode_t *, int); | ||||
|  |  | |||
|  | @ -1082,7 +1082,7 @@ xfs_unmountfs(xfs_mount_t *mp, struct cred *cr) | |||
| 	int64_t		fsid; | ||||
| #endif | ||||
| 
 | ||||
| 	xfs_iflush_all(mp, XFS_FLUSH_ALL); | ||||
| 	xfs_iflush_all(mp); | ||||
| 
 | ||||
| 	XFS_QM_DQPURGEALL(mp, | ||||
| 		XFS_QMOPT_UQUOTA | XFS_QMOPT_GQUOTA | XFS_QMOPT_UMOUNTING); | ||||
|  |  | |||
		Loading…
	
	Add table
		
		Reference in a new issue
	
	 Christoph Hellwig
						Christoph Hellwig