Index: uspace/lib/libfs/libfs.c
===================================================================
--- uspace/lib/libfs/libfs.c	(revision 0143f72c707fa87b2fc54b5d49db469471b06c40)
+++ uspace/lib/libfs/libfs.c	(revision bbf88db2c0682e7fe332dce82c3659c86fd7115c)
@@ -46,4 +46,19 @@
 #include <sys/stat.h>
 
+#define on_error(rc, action) \
+	do { \
+		if ((rc) != EOK) \
+			action; \
+	} while (0)
+
+#define combine_rc(rc1, rc2) \
+	((rc1) == EOK ? (rc2) : (rc1))
+
+#define answer_and_return(rid, rc) \
+	do { \
+		ipc_answer_0((rid), (rc)); \
+		return; \
+	} while (0)
+
 /** Register file system server.
  *
@@ -162,9 +177,10 @@
 	}
 
-	fs_node_t *fn = ops->node_get(mp_dev_handle, mp_fs_index);
-	if (!fn) {
+	fs_node_t *fn;
+	res = ops->node_get(&fn, mp_dev_handle, mp_fs_index);
+	if (res != EOK || !fn) {
 		ipc_hangup(mountee_phone);
-		ipc_answer_0(callid, ENOENT);
-		ipc_answer_0(rid, ENOENT);
+		ipc_answer_0(callid, combine_rc(res, ENOENT));
+		ipc_answer_0(rid, combine_rc(res, ENOENT));
 		return;
 	}
@@ -172,5 +188,5 @@
 	if (fn->mp_data.mp_active) {
 		ipc_hangup(mountee_phone);
-		ops->node_put(fn);
+		(void) ops->node_put(fn);
 		ipc_answer_0(callid, EBUSY);
 		ipc_answer_0(rid, EBUSY);
@@ -179,7 +195,7 @@
 
 	rc = async_req_0_0(mountee_phone, IPC_M_CONNECT_ME);
-	if (rc != 0) {
+	if (rc != EOK) {
 		ipc_hangup(mountee_phone);
-		ops->node_put(fn);
+		(void) ops->node_put(fn);
 		ipc_answer_0(callid, rc);
 		ipc_answer_0(rid, rc);
@@ -230,4 +246,5 @@
 	char component[NAME_MAX + 1];
 	int len;
+	int rc;
 
 	if (last < next)
@@ -235,6 +252,9 @@
 
 	fs_node_t *par = NULL;
-	fs_node_t *cur = ops->root_get(dev_handle);
+	fs_node_t *cur = NULL;
 	fs_node_t *tmp = NULL;
+
+	rc = ops->root_get(&cur, dev_handle);
+	on_error(rc, goto out_with_answer);
 
 	if (cur->mp_data.mp_active) {
@@ -242,5 +262,5 @@
 		    next, last, cur->mp_data.dev_handle, lflag, index,
 		    IPC_FF_ROUTE_FROM_ME);
-		ops->node_put(cur);
+		(void) ops->node_put(cur);
 		return;
 	}
@@ -249,5 +269,12 @@
 		next++;		/* eat slash */
 	
-	while (next <= last && ops->has_children(cur)) {
+	while (next <= last) {
+		bool has_children;
+
+		rc = ops->has_children(&has_children, cur);
+		on_error(rc, goto out_with_answer);
+		if (!has_children)
+			break;
+
 		/* collect the component */
 		len = 0;
@@ -267,5 +294,7 @@
 
 		/* match the component */
-		tmp = ops->match(cur, component);
+		rc = ops->match(&tmp, cur, component);
+		on_error(rc, goto out_with_answer);
+
 		if (tmp && tmp->mp_data.mp_active) {
 			if (next > last)
@@ -277,8 +306,8 @@
 			    VFS_OUT_LOOKUP, next, last, tmp->mp_data.dev_handle,
 			    lflag, index, IPC_FF_ROUTE_FROM_ME);
-			ops->node_put(cur);
-			ops->node_put(tmp);
+			(void) ops->node_put(cur);
+			(void) ops->node_put(tmp);
 			if (par)
-				ops->node_put(par);
+				(void) ops->node_put(par);
 			return;
 		}
@@ -300,16 +329,15 @@
 				fs_node_t *fn;
 				if (lflag & L_CREATE)
-					fn = ops->create(dev_handle, lflag);
+					rc = ops->create(&fn, dev_handle,
+					    lflag);
 				else
-					fn = ops->node_get(dev_handle,
+					rc = ops->node_get(&fn, dev_handle,
 					    index);
+				on_error(rc, goto out_with_answer);
 				if (fn) {
-					int rc;
-
 					rc = ops->link(cur, fn, component);
 					if (rc != EOK) {
-						if (lflag & L_CREATE) {
-							(void)ops->destroy(fn);
-						}
+						if (lflag & L_CREATE)
+							(void) ops->destroy(fn);
 						ipc_answer_0(rid, rc);
 					} else {
@@ -319,5 +347,5 @@
 						    ops->size_get(fn),
 						    ops->lnkcnt_get(fn));
-						ops->node_put(fn);
+						(void) ops->node_put(fn);
 					}
 				} else {
@@ -330,6 +358,8 @@
 		}
 
-		if (par)
-			ops->node_put(par);
+		if (par) {
+			rc = ops->node_put(par);
+			on_error(rc, goto out_with_answer);
+		}
 
 		/* descend one level */
@@ -340,5 +370,12 @@
 
 	/* handle miss: excessive components */
-	if (next <= last && !ops->has_children(cur)) {
+	if (next <= last) {
+		bool has_children;
+
+		rc = ops->has_children(&has_children, cur);
+		on_error(rc, goto out_with_answer);
+		if (has_children)
+			goto skip_miss;
+
 		if (lflag & (L_CREATE | L_LINK)) {
 			if (!ops->is_directory(cur)) {
@@ -368,14 +405,13 @@
 			fs_node_t *fn;
 			if (lflag & L_CREATE)
-				fn = ops->create(dev_handle, lflag);
+				rc = ops->create(&fn, dev_handle, lflag);
 			else
-				fn = ops->node_get(dev_handle, index);
+				rc = ops->node_get(&fn, dev_handle, index);
+			on_error(rc, goto out_with_answer);
 			if (fn) {
-				int rc;
-
 				rc = ops->link(cur, fn, component);
 				if (rc != EOK) {
 					if (lflag & L_CREATE)
-						(void)ops->destroy(fn);
+						(void) ops->destroy(fn);
 					ipc_answer_0(rid, rc);
 				} else {
@@ -385,5 +421,5 @@
 					    ops->size_get(fn),
 					    ops->lnkcnt_get(fn));
-					ops->node_put(fn);
+					(void) ops->node_put(fn);
 				}
 			} else {
@@ -395,10 +431,11 @@
 		goto out;
 	}
+skip_miss:
 
 	/* handle hit */
 	if (lflag & L_UNLINK) {
 		unsigned old_lnkcnt = ops->lnkcnt_get(cur);
-		int res = ops->unlink(par, cur, component);
-		ipc_answer_5(rid, (ipcarg_t)res, fs_handle, dev_handle,
+		rc = ops->unlink(par, cur, component);
+		ipc_answer_5(rid, (ipcarg_t)rc, fs_handle, dev_handle,
 		    ops->index_get(cur), ops->size_get(cur), old_lnkcnt);
 		goto out;
@@ -418,14 +455,20 @@
 	}
 
-	ipc_answer_5(rid, EOK, fs_handle, dev_handle, ops->index_get(cur),
-	    ops->size_get(cur), ops->lnkcnt_get(cur));
+out_with_answer:
+	if (rc == EOK) {
+		ipc_answer_5(rid, EOK, fs_handle, dev_handle,
+		    ops->index_get(cur), ops->size_get(cur),
+		    ops->lnkcnt_get(cur));
+	} else {
+		ipc_answer_0(rid, rc);
+	}
 
 out:
 	if (par)
-		ops->node_put(par);
+		(void) ops->node_put(par);
 	if (cur)
-		ops->node_put(cur);
+		(void) ops->node_put(cur);
 	if (tmp)
-		ops->node_put(tmp);
+		(void) ops->node_put(tmp);
 }
 
@@ -435,5 +478,9 @@
 	dev_handle_t dev_handle = (dev_handle_t) IPC_GET_ARG1(*request);
 	fs_index_t index = (fs_index_t) IPC_GET_ARG2(*request);
-	fs_node_t *fn = ops->node_get(dev_handle, index);
+	fs_node_t *fn;
+	int rc;
+
+	rc = ops->node_get(&fn, dev_handle, index);
+	on_error(rc, answer_and_return(rid, rc));
 
 	ipc_callid_t callid;
@@ -473,16 +520,19 @@
 	dev_handle_t dev_handle = IPC_GET_ARG1(*request);
 	fs_index_t index = IPC_GET_ARG2(*request);
-	
-	fs_node_t *node = ops->node_get(dev_handle, index);
-	
-	if (node == NULL) {
+	fs_node_t *fn;
+	int rc;
+	
+	rc = ops->node_get(&fn, dev_handle, index);
+	on_error(rc, answer_and_return(rid, rc));
+	
+	if (fn == NULL) {
 		ipc_answer_0(rid, ENOENT);
 		return;
 	}
 	
-	ipc_answer_5(rid, EOK, fs_handle, dev_handle, index,
-	    ops->size_get(node), ops->lnkcnt_get(node));
-	
-	ops->node_put(node);
+	ipc_answer_5(rid, EOK, fs_handle, dev_handle, index, ops->size_get(fn),
+	    ops->lnkcnt_get(fn));
+	
+	(void) ops->node_put(fn);
 }
 
Index: uspace/lib/libfs/libfs.h
===================================================================
--- uspace/lib/libfs/libfs.h	(revision 0143f72c707fa87b2fc54b5d49db469471b06c40)
+++ uspace/lib/libfs/libfs.h	(revision bbf88db2c0682e7fe332dce82c3659c86fd7115c)
@@ -56,16 +56,25 @@
 
 typedef struct {
-	fs_node_t * (* match)(fs_node_t *, const char *);
-	fs_node_t * (* node_get)(dev_handle_t, fs_index_t);
-	void (* node_put)(fs_node_t *);
-	fs_node_t * (* create)(dev_handle_t, int);
+	/*
+	 * The first set of methods are functions that return an integer error
+	 * code. If some additional return value is to be returned, the first
+	 * argument holds the output argument.
+	 */
+	int (* root_get)(fs_node_t **, dev_handle_t);
+	int (* match)(fs_node_t **, fs_node_t *, const char *);
+	int (* node_get)(fs_node_t **, dev_handle_t, fs_index_t);
+	int (* node_put)(fs_node_t *);
+	int (* create)(fs_node_t **, dev_handle_t, int);
 	int (* destroy)(fs_node_t *);
 	int (* link)(fs_node_t *, fs_node_t *, const char *);
 	int (* unlink)(fs_node_t *, fs_node_t *, const char *);
+	int (* has_children)(bool *, fs_node_t *);
+	/*
+	 * The second set of methods are usually mere getters that do not return
+	 * an integer error code.
+	 */
 	fs_index_t (* index_get)(fs_node_t *);
 	size_t (* size_get)(fs_node_t *);
 	unsigned (* lnkcnt_get)(fs_node_t *);
-	bool (* has_children)(fs_node_t *);
-	fs_node_t *(* root_get)(dev_handle_t);
 	char (* plb_get_char)(unsigned pos);
 	bool (* is_directory)(fs_node_t *);
