summaryrefslogtreecommitdiffstats
path: root/cpukit/libfs
diff options
context:
space:
mode:
authorJoel Sherrill <joel.sherrill@OARcorp.com>1999-11-05 21:10:54 +0000
committerJoel Sherrill <joel.sherrill@OARcorp.com>1999-11-05 21:10:54 +0000
commit94b357c2b31be20b51784dc6f2ae837d58777cbd (patch)
tree73e3ec3694451a65df6b0688e3e0e04175ea0528 /cpukit/libfs
parentRemoved. (diff)
downloadrtems-94b357c2b31be20b51784dc6f2ae837d58777cbd.tar.bz2
Unmount was failing as a side-effect of splitting the rmnod handler
and not handling every case properly.
Diffstat (limited to '')
-rw-r--r--cpukit/libfs/src/imfs/deviceio.c55
-rw-r--r--cpukit/libfs/src/imfs/imfs.h11
-rw-r--r--cpukit/libfs/src/imfs/imfs_eval.c2
-rw-r--r--cpukit/libfs/src/imfs/imfs_fsunmount.c7
-rw-r--r--cpukit/libfs/src/imfs/imfs_handlers_device.c2
-rw-r--r--cpukit/libfs/src/imfs/imfs_rmnod.c77
-rw-r--r--cpukit/libfs/src/imfs/imfs_unlink.c11
7 files changed, 102 insertions, 63 deletions
diff --git a/cpukit/libfs/src/imfs/deviceio.c b/cpukit/libfs/src/imfs/deviceio.c
index 70b9706ada..fd969e7aa9 100644
--- a/cpukit/libfs/src/imfs/deviceio.c
+++ b/cpukit/libfs/src/imfs/deviceio.c
@@ -212,60 +212,11 @@ int device_lseek(
/*
* device_stat
*
- * This IMFS_stat() is used.
+ * The IMFS_stat() is used.
*/
/*
* device_rmnod
+ *
+ * The IMFS_rmnod() is used.
*/
-
-int device_rmnod(
- rtems_filesystem_location_info_t *pathloc /* IN */
-)
-{
- IMFS_jnode_t *the_jnode;
-
- the_jnode = (IMFS_jnode_t *) pathloc->node_access;
-
- /*
- * Take the node out of the parent's chain that contains this node
- */
-
- if ( the_jnode->Parent != NULL ) {
- Chain_Extract( (Chain_Node *) the_jnode );
- the_jnode->Parent = NULL;
- }
-
- /*
- * Decrement the link counter and see if we can free the space.
- */
-
- the_jnode->st_nlink--;
- IMFS_update_ctime( the_jnode );
-
- /*
- * The file cannot be open and the link must be less than 1 to free.
- */
-
- if ( !rtems_libio_is_file_open( the_jnode ) && (the_jnode->st_nlink < 1) ) {
-
- /*
- * Is the rtems_filesystem_current is this node?
- */
-
- if ( rtems_filesystem_current.node_access == pathloc->node_access )
- rtems_filesystem_current.node_access = NULL;
-
- /*
- * Free memory associated with a memory file.
- */
-
- free( the_jnode );
- }
-
- return 0;
-
-}
-
-
-
diff --git a/cpukit/libfs/src/imfs/imfs.h b/cpukit/libfs/src/imfs/imfs.h
index a88672c4b8..ff76bcd04b 100644
--- a/cpukit/libfs/src/imfs/imfs.h
+++ b/cpukit/libfs/src/imfs/imfs.h
@@ -212,9 +212,10 @@ typedef enum {
* Shared Data
*/
+extern rtems_filesystem_file_handlers_r IMFS_directory_handlers;
extern rtems_filesystem_file_handlers_r IMFS_device_handlers;
+extern rtems_filesystem_file_handlers_r IMFS_link_handlers;
extern rtems_filesystem_file_handlers_r IMFS_memfile_handlers;
-extern rtems_filesystem_file_handlers_r IMFS_directory_handlers;
extern rtems_filesystem_operations_table IMFS_ops;
extern rtems_filesystem_operations_table miniIMFS_ops;
extern rtems_filesystem_limits_and_options_t IMFS_LIMITS_AND_OPTIONS;
@@ -456,10 +457,6 @@ int device_lseek(
int whence /* IN */
);
-int device_rmnod(
- rtems_filesystem_location_info_t *pathloc /* IN */
-);
-
int IMFS_utime(
rtems_filesystem_location_info_t *pathloc, /* IN */
time_t actime, /* IN */
@@ -492,6 +489,10 @@ int IMFS_fcntl(
rtems_libio_t *iop
);
+int IMFS_rmnod(
+ rtems_filesystem_location_info_t *pathloc /* IN */
+);
+
#ifdef __cplusplus
}
#endif
diff --git a/cpukit/libfs/src/imfs/imfs_eval.c b/cpukit/libfs/src/imfs/imfs_eval.c
index ee488f1a19..66b5fa828c 100644
--- a/cpukit/libfs/src/imfs/imfs_eval.c
+++ b/cpukit/libfs/src/imfs/imfs_eval.c
@@ -45,7 +45,7 @@ int IMFS_Set_handlers(
break;
case IMFS_SYM_LINK:
case IMFS_HARD_LINK:
- loc->handlers = &rtems_filesystem_null_handlers;
+ loc->handlers = &IMFS_link_handlers;
break;
case IMFS_MEMORY_FILE:
loc->handlers = fs_info->memfile_handlers;
diff --git a/cpukit/libfs/src/imfs/imfs_fsunmount.c b/cpukit/libfs/src/imfs/imfs_fsunmount.c
index 7a091c6fa3..9ca5f4c9fe 100644
--- a/cpukit/libfs/src/imfs/imfs_fsunmount.c
+++ b/cpukit/libfs/src/imfs/imfs_fsunmount.c
@@ -42,6 +42,11 @@
#define jnode_get_first_child( jnode ) \
((IMFS_jnode_t *)( Chain_Head( jnode_get_control( jnode ) )->next))
+/* XXX should be in a more public place */
+
+extern int IMFS_Set_handlers(
+ rtems_filesystem_location_info_t *loc
+);
int IMFS_fsunmount(
rtems_filesystem_mount_table_entry_t *temp_mt_entry
@@ -59,7 +64,6 @@ int IMFS_fsunmount(
jnode = (IMFS_jnode_t *)temp_mt_entry->mt_fs_root.node_access;
loc = temp_mt_entry->mt_fs_root;
-
/*
* Set this to null to indicate that it is being unmounted.
@@ -70,6 +74,7 @@ int IMFS_fsunmount(
do {
next = jnode->Parent;
loc.node_access = (void *)jnode;
+ IMFS_Set_handlers( &loc );
if ( jnode->type != IMFS_DIRECTORY ) {
result = IMFS_unlink( &loc );
diff --git a/cpukit/libfs/src/imfs/imfs_handlers_device.c b/cpukit/libfs/src/imfs/imfs_handlers_device.c
index 24b7ffa5bb..b6b9c808a0 100644
--- a/cpukit/libfs/src/imfs/imfs_handlers_device.c
+++ b/cpukit/libfs/src/imfs/imfs_handlers_device.c
@@ -34,5 +34,5 @@ rtems_filesystem_file_handlers_r IMFS_device_handlers = {
NULL, /* fsync */
NULL, /* fdatasync */
NULL, /* fcntl */
- device_rmnod
+ IMFS_rmnod
};
diff --git a/cpukit/libfs/src/imfs/imfs_rmnod.c b/cpukit/libfs/src/imfs/imfs_rmnod.c
new file mode 100644
index 0000000000..4707722e86
--- /dev/null
+++ b/cpukit/libfs/src/imfs/imfs_rmnod.c
@@ -0,0 +1,77 @@
+/*
+ * IMFS Node Removal Handler
+ *
+ * This file contains the handler used to remove a node when a file type
+ * does not require special actions.
+ *
+ * COPYRIGHT (c) 1989-1998.
+ * On-Line Applications Research Corporation (OAR).
+ * Copyright assigned to U.S. Government, 1994.
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.OARcorp.com/rtems/license.html.
+ *
+ * $Id$
+ */
+
+#include <rtems.h>
+#include <rtems/libio.h>
+#include "libio_.h"
+
+#include "imfs.h"
+
+/*
+ * IMFS_rmnod
+ */
+
+int IMFS_rmnod(
+ rtems_filesystem_location_info_t *pathloc /* IN */
+)
+{
+ IMFS_jnode_t *the_jnode;
+
+ the_jnode = (IMFS_jnode_t *) pathloc->node_access;
+
+ /*
+ * Take the node out of the parent's chain that contains this node
+ */
+
+ if ( the_jnode->Parent != NULL ) {
+ Chain_Extract( (Chain_Node *) the_jnode );
+ the_jnode->Parent = NULL;
+ }
+
+ /*
+ * Decrement the link counter and see if we can free the space.
+ */
+
+ the_jnode->st_nlink--;
+ IMFS_update_ctime( the_jnode );
+
+ /*
+ * The file cannot be open and the link must be less than 1 to free.
+ */
+
+ if ( !rtems_libio_is_file_open( the_jnode ) && (the_jnode->st_nlink < 1) ) {
+
+ /*
+ * Is the rtems_filesystem_current is this node?
+ */
+
+ if ( rtems_filesystem_current.node_access == pathloc->node_access )
+ rtems_filesystem_current.node_access = NULL;
+
+ /*
+ * Free memory associated with a memory file.
+ */
+
+ free( the_jnode );
+ }
+
+ return 0;
+
+}
+
+
+
diff --git a/cpukit/libfs/src/imfs/imfs_unlink.c b/cpukit/libfs/src/imfs/imfs_unlink.c
index e138064e61..03938937f4 100644
--- a/cpukit/libfs/src/imfs/imfs_unlink.c
+++ b/cpukit/libfs/src/imfs/imfs_unlink.c
@@ -49,9 +49,10 @@ int IMFS_unlink(
the_link.node_access = node->info.hard_link.link_node;
/*
- * If this is the last referance to the node
- * Free the node that the link points to.
+ * If removing the last hard link to a node, then we need
+ * to remove the node that is a link and the node itself.
*/
+
node->info.hard_link.link_node->st_nlink --;
IMFS_update_ctime( node->info.hard_link.link_node );
if ( node->info.hard_link.link_node->st_nlink < 1) {
@@ -61,7 +62,11 @@ int IMFS_unlink(
}
}
- result = (*loc->handlers->rmnod)( &the_link );
+ /*
+ * Now actually free the node we were asked to free.
+ */
+
+ result = (*loc->handlers->rmnod)( loc );
return result;
}