xref: /netbsd-src/share/man/man9/namei.9 (revision bdc22b2e01993381dcefeff2bc9b56ca75a4235c)
1.\"     $NetBSD: namei.9,v 1.50 2017/07/03 21:28:48 wiz Exp $
2.\"
3.\" Copyright (c) 2001, 2005, 2006, 2017 The NetBSD Foundation, Inc.
4.\" All rights reserved.
5.\"
6.\" This code is derived from software contributed to The NetBSD Foundation
7.\" by Gregory McGarry.
8.\"
9.\" Redistribution and use in source and binary forms, with or without
10.\" modification, are permitted provided that the following conditions
11.\" are met:
12.\" 1. Redistributions of source code must retain the above copyright
13.\"    notice, this list of conditions and the following disclaimer.
14.\" 2. Redistributions in binary form must reproduce the above copyright
15.\"    notice, this list of conditions and the following disclaimer in the
16.\"    documentation and/or other materials provided with the distribution.
17.\"
18.\" THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
19.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
20.\" TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
21.\" PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
22.\" BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23.\" CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
24.\" SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
25.\" INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
26.\" CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28.\" POSSIBILITY OF SUCH DAMAGE.
29.\"
30.Dd March 18, 2017
31.Dt NAMEI 9
32.Os
33.Sh NAME
34.Nm namei ,
35.Nm NDINIT ,
36.Nm NDAT ,
37.Nm namei_simple_kernel ,
38.Nm namei_simple_user ,
39.Nm relookup ,
40.Nm lookup_for_nfsd ,
41.Nm lookup_for_nfsd_index
42.Nd pathname lookup
43.Sh SYNOPSIS
44.In sys/namei.h
45.In sys/uio.h
46.In sys/vnode.h
47.Fn NDINIT "struct nameidata *ndp" "u_long op" "u_long flags" \
48"struct pathbuf *pathbuf"
49.Fn NDAT "struct nameidata *ndp" "struct vnode *dvp"
50.Ft int
51.Fn namei "struct nameidata *ndp"
52.Ft int
53.Fn namei_simple_kernel "const char *path" "namei_simple_flags_t sflags" \
54"struct vnode **ret"
55.Ft int
56.Fn namei_simple_user "const char *path" "namei_simple_flags_t sflags" \
57"struct vnode **ret"
58.Ft int
59.Fn relookup "struct vnode *dvp" "struct vnode **vpp" \
60"struct componentname *cnp"
61.Ft int
62.Fn lookup_for_nfsd "struct nameidata *ndp" "struct vnode *startdir" \
63"int neverfollow"
64.Ft int
65.Fn lookup_for_nfsd_index "struct nameidata *ndp"
66.Sh DESCRIPTION
67The
68.Nm
69interface is used to convert pathnames to file system vnodes.
70The
71name of the interface is actually a contraction of the words
72.Em name
73and
74.Em inode
75for name-to-inode conversion, in the days before the
76.Xr vfs 9
77interface was implemented.
78.Pp
79All access to the
80.Nm
81interface must be in process context.
82Pathname lookups cannot be done in interrupt context.
83.Pp
84In the general form of
85.Nm ,
86a caller must:
87.Bl -enum -compact
88.It
89Allocate storage for a
90.Ft struct nameidata
91object
92.Fa nd .
93.It
94Initialize
95.Fa nd
96with
97.Fn NDINIT
98and optionally
99.Fn NDAT
100to specify the arguments to a lookup.
101.It
102Call
103.Fn namei
104and handle failure if it returns a nonzero error code.
105.It
106Read the resulting vnode out of
107.Fa nd Ns Li .ni_vp .
108If requested with
109.Dv LOCKPARENT ,
110read the directory vnode out of
111.Fa nd Ns Li .ni_dvp .
112.It
113For directory operations, use the
114.Ft struct componentname
115object stored at
116.Fa nd Ns Li .ni_cnd .
117.El
118.Pp
119The other fields of
120.Ft struct nameidata
121should not be examined or altered directly.
122.Pp
123Note that the
124.Xr nfs 4
125code misuses
126.Ft struct nameidata
127and currently has an incestuous relationship with the
128.Nm
129code.
130This is gradually being cleaned up.
131.Pp
132The
133.Ft struct componentname
134type has the following layout:
135.Bd -literal
136struct componentname {
137	/*
138	 * Arguments to VOP_LOOKUP and directory VOP routines.
139	 */
140	uint32_t	cn_nameiop;	/* namei operation */
141	uint32_t	cn_flags;	/* flags to namei */
142	kauth_cred_t 	cn_cred;	/* credentials */
143	const char 	*cn_nameptr;	/* pointer to looked up name */
144	size_t		cn_namelen;	/* length of looked up comp */
145	/*
146	 * Side result from VOP_LOOKUP.
147	 */
148	size_t		cn_consume;	/* chars to consume in lookup */
149};
150.Ed
151.Pp
152This structure contains the information about a single directory
153component name, along with certain other information required by vnode
154operations.
155See
156.Xr vnodeops 9
157for more information about these vnode operations.
158.Pp
159The members:
160.Bl -tag -offset indent -width cn_consumexx -compact
161.It cn_nameiop
162The type of operation in progress; indicates the basic operating mode
163of namei.
164May be one of
165.Dv LOOKUP ,
166.Dv CREATE ,
167.Dv DELETE ,
168or
169.Dv RENAME .
170These modes are described below.
171.It cn_flags
172Additional flags affecting the operation of namei.
173These are described below as well.
174.It cn_cred
175The credentials to use for the lookup or other operation the
176.Em componentname
177is passed to.
178This may match the credentials of the current process or it may not,
179depending on where the original operation request came from and how it
180has been routed.
181.It cn_nameptr
182The name of this directory component, followed by the rest of the path
183being looked up.
184.It cn_namelen
185The length of the name of this directory component.
186The name is not in general null terminated, although the complete
187string (the full remaining path) always is.
188.It cn_consume
189This field starts at zero; it may be set to a larger value by
190implementations of
191.Xr VOP_LOOKUP 9
192to indicate how many more characters beyond
193.Em cn_namelen
194are being consumed.
195New uses of this feature are discouraged and should be discussed.
196.El
197.Ss Operating modes
198Each lookup happens in one of the following modes, specified by
199callers of
200.Nm
201with
202.Fn NDINIT
203and specified internally by
204.Nm
205to
206.Xr VOP_LOOKUP 9 :
207.Bl -bullet -compact
208.It
209Callers of
210.Nm
211specify the mode for the last component of a lookup.
212.It
213Internally,
214.Nm
215recursively calls
216.Xr VOP_LOOKUP 9
217in
218.Dv LOOKUP
219mode for each directory component, and then finally calls
220.Xr VOP_LOOKUP 9
221in the caller-specified mode for the last component.
222.El
223Each mode can fail in different ways \(em for example,
224.Dv LOOKUP
225mode fails with
226.Er ENOENT
227if no entry exists, but
228.Dv CREATE
229mode succeeds with a
230.Dv NULL
231vnode.
232.Bl -tag -width LOOKUP
233.It Dv LOOKUP
234Yield the vnode for an existing entry.
235Callers specify
236.Dv LOOKUP
237for operations on existing vnodes:
238.Xr stat 2 ,
239.Xr open 2
240without
241.Dv O_CREATE ,
242etc.
243.Pp
244File systems:
245.Bl -dash -compact
246.It
247MUST refuse if user lacks lookup permission for directory.
248.It
249SHOULD use
250.Xr namecache 9
251to cache lookup results.
252.El
253.Pp
254.Bl -tag -compact -width ENAMETOOLONG
255.It Bq Er ENOENT
256No entry exists.
257.El
258.It Dv CREATE
259Yield the vnode for an existing entry; or, if there is none, yield
260.Dv NULL
261and hint that it will soon be created.
262Callers specify
263.Dv CREATE
264for operations that may create directory entries:
265.Xr mkdir 2 ,
266.Xr open 2
267with
268.Dv O_CREATE ,
269etc.
270.Pp
271File systems:
272.Bl -dash -compact
273.It
274MUST refuse if user lacks lookup permission for directory.
275.It
276MUST refuse if no entry exists and user lacks write permission for
277directory.
278.It
279MUST refuse if no entry exists and file system is read-only.
280.It
281SHOULD NOT use
282.Xr namecache 9
283to cache negative lookup results.
284.It
285SHOULD save lookup hints internally in the directory for a subsequent
286operation to create a directory entry.
287.El
288.Pp
289.Bl -tag -compact -width ENAMETOOLONG
290.It Bq Er EPERM
291The user lacks lookup permission for the directory.
292.It Bq Er EPERM
293No entry exists and the user lacks write permission for the directory.
294.It Bq Er EROFS
295No entry exists and the file system is read-only.
296.El
297.It Dv DELETE
298Yield the vnode of an existing entry, and hint that it will soon be
299deleted.
300Callers specify
301.Dv DELETE
302for operations that delete directory entries:
303.Xr unlink 2 ,
304.Xr rmdir 2 ,
305etc.
306.Pp
307File systems:
308.Bl -dash -compact
309.It
310MUST refuse if user lacks lookup permission for directory.
311.It
312MUST refuse if entry exists and user lacks write permission for
313directory.
314.It
315MUST refuse if entry exists and file system is read-only.
316.It
317SHOULD NOT use
318.Xr namecache 9
319to cache lookup results.
320.It
321SHOULD save lookup hints internally in the directory for a subsequent
322operation to delete a directory entry.
323.El
324.Pp
325.Bl -tag -compact -width ENAMETOOLONG
326.It Bq Er ENOENT
327No entry exists.
328.It Bq Er EPERM
329The user lacks lookup permission for the directory.
330.It Bq Er EPERM
331An entry exists and the user lacks write permission for the directory.
332.It Bq Er EROFS
333An entry exists and the file system is read-only.
334.El
335.It Dv RENAME
336Yield the vnode of an existing entry, and hint that it will soon be
337overwritten; or, if there is none, yield
338.Dv NULL ,
339and hint that it will soon be created.
340.Pp
341Callers specify
342.Dv RENAME
343for an entry that is about to be created or overwritten, namely for the
344target of
345.Xr rename 2 .
346.Pp
347File systems:
348.Bl -dash -compact
349.It
350MUST refuse if user lacks lookup permission for directory.
351.It
352MUST refuse if user lacks write permission for directory.
353.It
354MUST refuse if file system is read-only.
355.It
356SHOULD NOT use
357.Xr namecache 9
358to cache lookup results.
359.It
360SHOULD save lookup hints internally in the directory for a subsequent
361operation to create or overwrite a directory entry.
362.El
363.Pp
364.Bl -tag -compact -width ENAMETOOLONG
365.It Bq Er EPERM
366The user lacks lookup permission for the directory.
367.It Bq Er EPERM
368The user lacks write permission for the directory.
369.It Bq Er EROFS
370The file system is read-only.
371.El
372.El
373.Pp
374If a caller decides not to perform an operation it hinted at by a
375destructive operating mode
376.Pq Dv CREATE , Dv DELETE , No or Dv RENAME ,
377it SHOULD call
378.Xr VOP_ABORTOP 9
379to release the hints.
380If a file system fails to perform such an operation, it SHOULD call
381.Xr VOP_ABORTOP 9
382to release the hints.
383However, the current code is inconsistent about this, and every
384implementation of
385.Xr VOP_ABORTOP 9
386does nothing.
387.Ss Flags
388The following flags may be specified by
389.Em callers
390of
391.Nm ,
392and MUST NOT be used by file systems:
393.Bl -tag -width NOCROSSMOUNT
394.It Dv FOLLOW
395Follow symbolic links in the last path component.
396Used by operations that do not address symbolic links directly, such as
397.Xr stat 2 .
398(Does not affect symbolic links found in the middle of a path.)
399.It Dv NOFOLLOW
400Do not follow symbolic links in the last path component.
401Used by operations that address symbolic links directly, such as
402.Xr lstat 2 .
403.Pp
404Note: The value of
405.Dv NOFOLLOW
406is 0.
407We define the constant to let callers say either
408.Dv FOLLOW
409or
410.Dv NOFOLLOW
411explicitly.
412.It Dv LOCKLEAF
413On successful lookup, lock the vnode, if any, in
414.Fa ndp Ns Li ->ni_vp .
415Without this flag, it would be unlocked.
416.It Dv LOCKPARENT
417On successful lookup, lock and return the directory vnode in
418.Fa ndp Ns Li ->ni_dvp .
419Without this flag, it is not returned at all.
420.It Dv TRYEMULROOT
421If set, the path is looked up in the emulation root of the current
422process first.
423If that fails, the system root is used.
424.It Dv EMULROOTSET
425Indicates that the caller has set
426.Fa ndp Ns Li ->ni_erootdir
427prior to calling
428.Nm .
429This is only useful or permitted when the emulation in the current
430process is partway through being set up.
431.It Dv NOCHROOT
432Bypass normal
433.Xr chroot 8
434handling for absolute paths.
435.It Dv NOCROSSMOUNT
436Do not cross mount points.
437.It Dv RDONLY
438Enforce read-only behavior.
439.It Dv CREATEDIR
440Accept slashes after a component name that does not exist.
441This only makes sense in
442.Dv CREATE
443mode and when creating a directory.
444.It Dv NOCACHE
445Do not cache the lookup result for the last component name.
446This is used only with the
447.Dv RENAME
448mode for the target; the cache entry would be invalidated immediately.
449.El
450.Pp
451The following flag may be set by a caller of
452.Nm
453and tested by a file system in
454.Xr VOP_LOOKUP 9
455or other subsequent directory operations:
456.Bl -tag -width NOCROSSMOUNT
457.It Dv DOWHITEOUT
458Allow whiteouts to be seen as objects instead of functioning as
459.Dq nothing there .
460.El
461.Pp
462The following flags are set by namei for calling
463.Xr VOP_LOOKUP 9 :
464.Bl -tag -width NOCROSSMOUNT
465.It Dv ISDOTDOT
466The current pathname component is
467.Dq Li .. .
468May be tested by subsequent directory operations too.
469.It Dv ISLASTCN
470The current pathname component is the last component found in the
471pathname.
472Guaranteed to remain set in subsequent directory operations.
473.It Dv REQUIREDIR
474The current object to be looked up must be a directory.
475May not be used by subsequent directory operations.
476.It Dv MAKEENTRY
477The lookup result for the current pathname component should be added to
478the
479.Xr namecache 9 .
480May be used to make additional caching decisions, e.g. to store an
481mtime for determining whether our cache for a remote vnode is stale.
482May not be used by subsequent directory operatoins.
483.El
484.Pp
485A file system may set the following flag on return from
486.Xr VOP_LOOKUP 9
487for use by
488.Nm ,
489.Xr namecache 9 ,
490and subsequent directory operations:
491.Bl -tag -width NOCROSSMOUNT
492.It Dv ISWHITEOUT
493The object at the current pathname component is a whiteout.
494.El
495.Pp
496The following additional historic flags have been removed from
497.Nx
498and should be handled as follows if porting code from elsewhere:
499.Bl -tag -width NOCROSSMOUNT
500.It Dv INRENAME
501Part of a misbegotten and incorrect locking scheme.
502Any file-system-level code using this is presumptively incorrect.
503File systems should use the
504.Xr genfs_rename 9
505interface to handle locking in
506.Fn VOP_RENAME .
507.It Dv INRELOOKUP
508Used at one point for signaling to
509.Xr puffs 3
510to work around a protocol deficiency that was later rectified.
511.It Dv ISSYMLINK
512Useless internal state.
513.It Dv SAVESTART
514Unclean setting affect vnode reference counting.
515Now effectively never in effect.
516Any code referring to this is suspect.
517.It Dv SAVENAME
518Unclean setting relating to responsibility for freeing pathname buffers
519in the days before the
520.Em pathbuf
521structure.
522Now effectively always in effect; the caller of
523.Nm
524owns the
525.Em pathbuf
526structure and is always responsible for destroying it.
527.It Dv HASBUF
528Related to SAVENAME.
529Any uses can be replaced with
530.Dq true .
531.El
532.Sh FUNCTIONS
533.Bl -tag -width abcd
534.It Fn NDINIT "ndp" "op" "flags" "pathbuf"
535Initialise a nameidata structure pointed to by
536.Fa ndp
537for use by the
538.Nm
539interface.
540The operating mode and flags (as documented above) are specified by
541.Fa op
542and
543.Fa flags
544respectively.
545The pathname is passed as a pathbuf structure, which should be
546initialized using one of the
547.Xr pathbuf 9
548operations.
549Destroying the pathbuf is the responsibility of the caller; this must
550not be done until the caller is finished with all of the
551.Nm
552results and all of the nameidata contents except for the result vnode.
553.Pp
554This routine stores the credentials of the calling thread
555.Va ( curlwp )
556in
557.Fa ndp .
558.Fn NDINIT
559sets the credentials using
560.Xr kauth_cred_get 9 .
561In the rare case that another set of credentials is required for the
562namei operation,
563.Em ndp->ni_cnd.cn_cred
564must be set manually after
565.Fn NDINIT .
566.It Fn NDAT "ndp" "dvp"
567This macro is used after
568.Fn NDINIT
569to set the starting directory.
570This supersedes the current process's current working directory as the
571initial point of departure for looking up relative paths.
572This mechanism is used by
573.Xr openat 2
574and related calls.
575.It Fn namei "ndp"
576Convert a pathname into a pointer to a vnode.
577The nameidata structure pointed to by
578.Fa ndp
579should be initialized with the
580.Fn NDINIT
581macro, and perhaps also the
582.Fn NDAT
583macro.
584Direct initialization of members of struct nameidata is
585.Em not
586supported and may (will) break silently in the future.
587.Pp
588The vnode for the pathname is returned in
589.Em ndp->ni_vp .
590The parent directory is returned locked in
591.Em ndp->ni_dvp
592iff
593.Dv LOCKPARENT
594is specified.
595.Pp
596Any or all of the flags documented above as set by the caller can be
597enabled by passing them (OR'd together) as the
598.Fa flags
599argument of
600.Fn NDINIT .
601As discussed above every such call should explicitly contain either
602.Dv FOLLOW
603or
604.Dv NOFOLLOW
605to control the behavior regarding final symbolic links.
606.It Fn namei_simple_kernel "path" "sflags" "ret"
607Look up the path
608.Fa path
609and translate it to a vnode, returned in
610.Fa ret .
611The
612.Fa path
613argument must be a kernel
614.Pq Dv UIO_SYSSPACE
615pointer.
616The
617.Fa sflags
618argument chooses the precise behavior.
619It may be set to one of the following symbols:
620.Bl -tag -offset indent -width NSM_NOFOLLOW_TRYEMULROOT -compact
621.It Dv NSM_NOFOLLOW_NOEMULROOT
622.It Dv NSM_NOFOLLOW_TRYEMULROOT
623.It Dv NSM_FOLLOW_NOEMULROOT
624.It Dv NSM_FOLLOW_TRYEMULROOT
625.El
626These select (or not) the
627.Dv FOLLOW/NOFOLLOW
628and
629.Dv TRYEMULROOT
630flags.
631Other flags are not available through this interface, which is
632nonetheless sufficient for more than half the
633.Fn namei
634usage in the kernel.
635Note that the encoding of
636.Fa sflags
637has deliberately been arranged to be type-incompatible with anything
638else.
639This prevents various possible accidents while the
640.Fn namei
641interface is being rototilled.
642.It Fn namei_simple_user "path" "sflags" "ret"
643This function is the same as
644.Fn namei_simple_kernel
645except that the
646.Fa path
647argument shall be a user pointer
648.Pq Dv UIO_USERSPACE
649rather than a kernel pointer.
650.It Fn relookup "dvp" "vpp" "cnp"
651Reacquire a path name component is a directory.
652This is a quicker way to lookup a pathname component when the parent
653directory is known.
654The locked parent directory vnode is specified by
655.Fa dvp
656and the pathname component by
657.Fa cnp .
658The vnode of the pathname is returned in the address specified by
659.Fa vpp .
660Note that one may only use
661.Fn relookup
662to repeat a lookup of a final path component previously done by
663.Nm ,
664and one must use the same
665.Em componentname
666structure that call produced.
667Otherwise the behavior is undefined and likely adverse.
668.It Fn lookup_for_nfsd "ndp" "startdir" "neverfollow"
669This is a private entry point into
670.Nm
671used by the NFS server code.
672It looks up a path starting from
673.Fa startdir .
674If
675.Fa neverfollow
676is set,
677.Em any
678symbolic link (not just at the end of the path) will cause an error.
679Otherwise, it follows symlinks normally.
680It should not be used by new code.
681.It Fn lookup_for_nfsd_index "ndp"
682This is a (second) private entry point into
683.Nm
684used by the NFS server code.
685It looks up a single path component.
686It should not be used by new code.
687.El
688.Sh INTERNALS
689The
690.Em nameidata
691structure has the following layout:
692.Bd -literal
693struct nameidata {
694	/*
695	 * Arguments to namei.
696	 */
697	struct vnode *ni_atdir;		/* startup dir, cwd if null */
698	struct pathbuf *ni_pathbuf;	/* pathname container */
699	char *ni_pnbuf;			/* extra pathname buffer ref (XXX) */
700	/*
701	 * Internal starting state. (But see notes.)
702	 */
703	struct	vnode *ni_rootdir;	/* logical root directory */
704	struct	vnode *ni_erootdir;	/* emulation root directory */
705	/*
706	 * Results from namei.
707	 */
708	struct	vnode *ni_vp;		/* vnode of result */
709	struct	vnode *ni_dvp;		/* vnode of intermediate directory */
710	/*
711	 * Internal current state.
712	 */
713	size_t		ni_pathlen;	/* remaining chars in path */
714	const char	*ni_next;	/* next location in pathname */
715	unsigned int	ni_loopcnt;	/* count of symlinks encountered */
716	/*
717	 * Lookup parameters: this structure describes the subset of
718	 * information from the nameidata structure that is passed
719	 * through the VOP interface.
720	 */
721	struct componentname ni_cnd;
722};
723.Ed
724.Pp
725These fields are:
726.Bl -tag -offset indent -width ni_erootdirx -compact
727.It ni_atdir
728The directory to use for the starting point of relative paths.
729If null, the current process's current directory is used.
730This is initialized to
731.Dv NULL
732by
733.Fn NDINIT
734and set by
735.Fn NDAT .
736.It ni_pathbuf
737The abstract path buffer in use, passed as an argument to
738.Fn NDINIT .
739The name pointers that appear elsewhere, such as in the
740.Em componentname
741structure, point into this buffer.
742It is owned by the caller and must not be destroyed until all
743.Nm
744operations are complete.
745See
746.Xr pathbuf 9 .
747.It ni_pnbuf
748This is the name pointer used during
749.Nm .
750It points into
751.Fa ni_pathbuf .
752It is not initialized until entry into
753.Nm .
754.It ni_rootdir
755The root directory to use as the starting point for absolute paths.
756This is retrieved from the current process's current root directory
757when
758.Nm
759starts up.
760It is not initialized by
761.Fn NDINIT .
762.It ni_erootdir
763The root directory to use as the emulation root, for processes running
764in emulation.
765This is retrieved from the current process's emulation root directory
766when
767.Nm
768starts up and not initialized by
769.Fn NDINIT .
770As described elsewhere, it may be set by the caller if the
771.Dv EMULROOTSET
772flag is used, but this should only be done when the current process's
773emulation root directory is not yet initialized.
774(And ideally in the future things would be tidied so that this is not
775necessary.)
776.It ni_vp
777.It ni_dvp
778Returned vnodes, as described above.
779These only contain valid values if
780.Nm
781returns successfully.
782.It ni_pathlen
783The length of the full current remaining path string in
784.Fa ni_pnbuf .
785This is not initialized by
786.Fn NDINIT
787and is used only internally.
788.It ni_next
789The remaining part of the path, after the current component found in
790the
791.Em componentname
792structure.
793This is not initialized by
794.Fn NDINIT
795and is used only internally.
796.It ni_loopcnt
797The number of symbolic links encountered (and traversed) so far.
798If this exceeds a limit,
799.Nm
800fails with
801.Er ELOOP .
802This is not initialized by
803.Fn NDINIT
804and is used only internally.
805.It ni_cnd
806The
807.Em componentname
808structure holding the current directory component, and also the
809mode, flags, and credentials.
810The mode, flags, and credentials are initialized by
811.Fn NDINIT ;
812the rest is not initialized until
813.Nm
814runs.
815.El
816.Pp
817There is also a
818.Em namei_state
819structure that is hidden within
820.Pa vfs_lookup.c .
821This contains the following additional state:
822.Bl -tag -offset indent -width attempt_retry -compact
823.It docache
824A flag indicating whether to cache the last pathname component.
825.It rdonly
826The read-only state, initialized from the
827.Dv RDONLY
828flag.
829.It slashes
830The number of trailing slashes found after the current pathname
831component.
832.It attempt_retry
833Set on some error cases (and not others) to indicate that a failure in
834the emulation root should be followed by a retry in the real system
835root.
836.El
837.Pp
838The state in
839.Em namei_state
840is genuinely private to
841.Nm .
842Note that much of the state in
843.Em nameidata
844should also be private, but is currently not because it is misused in
845some fashion by outside code, usually
846.Xr nfs 4 .
847.Pp
848The control flow within the
849.Nm
850portions of
851.Pa vfs_lookup.c
852is as follows.
853.Bl -tag -width namei_tryemulrootXX
854.It Fn namei
855does a complete path lookup by calling
856.Fn namei_init ,
857.Fn namei_tryemulroot ,
858and
859.Fn namei_cleanup .
860.It Fn namei_init
861sets up the basic internal state and makes some (precondition-type)
862assertions.
863.It Fn namei_cleanup
864makes some postcondition-type assertions; it currently does nothing
865besides this.
866.It Fn namei_tryemulroot
867handles
868.Dv TRYEMULROOT
869by calling
870.Fn namei_oneroot
871once or twice as needed, and attends to making sure the original
872pathname is preserved for the second try.
873.It Fn namei_oneroot
874does a complete path search from a single root directory.
875It begins with
876.Fn namei_start ,
877then calls
878.Fn lookup_once
879(and if necessary,
880.Fn namei_follow )
881repeatedly until done.
882It also handles returning the result vnode(s) in the requested state.
883.It Fn namei_start
884sets up the initial state and locking; it calls
885.Fn namei_getstartdir .
886.It Fn namei_getstartdir
887initializes the root directory state (both
888.Fa ni_rootdir
889and
890.Fa ni_erootdir )
891and picks the starting directory, consuming the leading slashes of an
892absolute path and handling the magic
893.Dq /../
894string for bypassing the emulation root.
895A different version
896.Fn namei_getstartdir_for_nfsd
897is used for lookups coming from
898.Xr nfsd 8
899as those are required to have different semantics.
900.It Fn lookup_once
901calls
902.Fn VOP_LOOKUP
903for one path component, also handling any needed crossing of mount
904points (either up or down) and coping with locking requirements.
905.It Fn lookup_parsepath
906is called prior to each
907.Fn lookup_once
908call to examine the pathname and find where the next component
909starts.
910.It Fn namei_follow
911reads the contents of a symbolic link and updates both the path buffer
912and the search directory accordingly.
913.El
914.Pp
915As a final note be advised that the magic return value associated with
916.Dv CREATE
917mode is different for
918.Nm
919than it is for
920.Fn VOP_LOOKUP .
921The latter
922.Dq fails
923with
924.Er EJUSTRETURN .
925.Nm
926translates this into succeeding and returning a null vnode.
927.Sh CODE REFERENCES
928The name lookup subsystem is implemented within the file
929.Pa sys/kern/vfs_lookup.c .
930.Sh SEE ALSO
931.Xr intro 9 ,
932.Xr namecache 9 ,
933.Xr vfs 9 ,
934.Xr vnode 9 ,
935.Xr vnodeops 9
936.Sh BUGS
937There should be no such thing as operating modes.
938Only
939.Dv LOOKUP
940is actually needed.
941The behavior where removing an object looks it up within
942.Nm
943and then calls into the file system (which must look it up again
944internally or cache state from
945.Fn VOP_LOOKUP )
946is particularly contorted.
947.Pp
948Most of the flags are equally bogus.
949.Pp
950Most of the contents of the
951.Em nameidata
952structure should be private and hidden within
953.Nm ;
954currently it cannot be because of abuse elsewhere.
955.Pp
956The
957.Dv EMULROOTSET
958flag is messy.
959.Pp
960There is no good way to support file systems that want to use
961a more elaborate pathname schema than the customary slash-delimited
962components.
963