xref: /minix3/minix/lib/libvtreefs/path.c (revision c21aa858e206a580693d3705485ebfc26ae29170)
1693ad767SDavid van Moolenbroek /* VTreeFS - path.c - name resolution */
2433d6423SLionel Sambuc 
3433d6423SLionel Sambuc #include "inc.h"
4433d6423SLionel Sambuc 
5693ad767SDavid van Moolenbroek /*
6693ad767SDavid van Moolenbroek  * Resolve a path string to an inode.
7693ad767SDavid van Moolenbroek  */
8693ad767SDavid van Moolenbroek int
fs_lookup(ino_t dir_nr,char * name,struct fsdriver_node * node_details,int * is_mountpt)9693ad767SDavid van Moolenbroek fs_lookup(ino_t dir_nr, char * name, struct fsdriver_node * node_details,
100dc5c83eSDavid van Moolenbroek 	int * is_mountpt)
11433d6423SLionel Sambuc {
120dc5c83eSDavid van Moolenbroek 	struct inode *node, *child;
130dc5c83eSDavid van Moolenbroek 	int r;
14433d6423SLionel Sambuc 
150dc5c83eSDavid van Moolenbroek 	if ((node = find_inode(dir_nr)) == NULL)
16433d6423SLionel Sambuc 		return EINVAL;
17433d6423SLionel Sambuc 
180dc5c83eSDavid van Moolenbroek 	if (!S_ISDIR(node->i_stat.mode))
190dc5c83eSDavid van Moolenbroek 		return ENOTDIR;
20433d6423SLionel Sambuc 
21*c21aa858SCristiano Giuffrida 	if (strlen(name) > NAME_MAX)
220dc5c83eSDavid van Moolenbroek 		return ENAMETOOLONG;
23433d6423SLionel Sambuc 
240dc5c83eSDavid van Moolenbroek 	if (!strcmp(name, ".")) {
250dc5c83eSDavid van Moolenbroek 		/* Stay in the given directory. */
260dc5c83eSDavid van Moolenbroek 		child = node;
270dc5c83eSDavid van Moolenbroek 	} else if (!strcmp(name, "..")) {
280dc5c83eSDavid van Moolenbroek 		/* Progress into the parent directory. */
290dc5c83eSDavid van Moolenbroek 		if ((child = get_parent_inode(node)) == NULL)
300dc5c83eSDavid van Moolenbroek 			return ENOENT;	/* deleted? should not be possible */
31433d6423SLionel Sambuc 	} else {
320dc5c83eSDavid van Moolenbroek 		/* Progress into a directory entry.  Call the lookup hook, if
330dc5c83eSDavid van Moolenbroek 		 * present, before doing the actual lookup.
34433d6423SLionel Sambuc 		 */
350dc5c83eSDavid van Moolenbroek 		if (!is_inode_deleted(node) &&
360dc5c83eSDavid van Moolenbroek 		    vtreefs_hooks->lookup_hook != NULL) {
370dc5c83eSDavid van Moolenbroek 			r = vtreefs_hooks->lookup_hook(node, name,
380dc5c83eSDavid van Moolenbroek 			    get_inode_cbdata(node));
390dc5c83eSDavid van Moolenbroek 			if (r != OK) return r;
40433d6423SLionel Sambuc 		}
41433d6423SLionel Sambuc 
420dc5c83eSDavid van Moolenbroek 		if ((child = get_inode_by_name(node, name)) == NULL)
430dc5c83eSDavid van Moolenbroek 			return ENOENT;
44433d6423SLionel Sambuc 	}
45433d6423SLionel Sambuc 
460dc5c83eSDavid van Moolenbroek 	/* On success, open the resulting file and return its details. */
470dc5c83eSDavid van Moolenbroek 	ref_inode(child);
48433d6423SLionel Sambuc 
490dc5c83eSDavid van Moolenbroek 	node_details->fn_ino_nr = get_inode_number(child);
500dc5c83eSDavid van Moolenbroek 	node_details->fn_mode = child->i_stat.mode;
510dc5c83eSDavid van Moolenbroek 	node_details->fn_size = child->i_stat.size;
520dc5c83eSDavid van Moolenbroek 	node_details->fn_uid = child->i_stat.uid;
530dc5c83eSDavid van Moolenbroek 	node_details->fn_gid = child->i_stat.gid;
540dc5c83eSDavid van Moolenbroek 	node_details->fn_dev = child->i_stat.dev;
55433d6423SLionel Sambuc 
560dc5c83eSDavid van Moolenbroek 	*is_mountpt = FALSE;
57433d6423SLionel Sambuc 
58433d6423SLionel Sambuc 	return OK;
59433d6423SLionel Sambuc }
60