source: rtems/c/src/lib/libc/mount.c @ 04df848

4.104.114.84.95
Last change on this file since 04df848 was 04df848, checked in by Jennifer Averett <Jennifer.Averett@…>, on 10/25/99 at 14:23:03

Added code to correctly free any allocated space during the evaluation
process.

  • Property mode set to 100644
File size: 7.0 KB
Line 
1/*
2 *  mount()
3 *
4 *  XXX
5 *
6 *  XXX make sure no required ops are NULL
7 *  XXX make sure no optional ops you are using are NULL
8 *  XXX unmount should be required.
9 *
10 *  COPYRIGHT (c) 1989-1998.
11 *  On-Line Applications Research Corporation (OAR).
12 *  Copyright assigned to U.S. Government, 1994.
13 *
14 *  The license and distribution terms for this file may be
15 *  found in the file LICENSE in this distribution or at
16 *  http://www.OARcorp.com/rtems/license.html.
17 *
18 *  $Id$
19 */
20
21#include <sys/types.h>
22#include <sys/stat.h>
23#include <chain.h>
24#include <fcntl.h>
25#include <unistd.h>
26#include <errno.h>
27#include <stdlib.h>
28#include <string.h>
29#include <assert.h>
30
31#include "libio_.h"
32
33Chain_Control rtems_filesystem_mount_table_control;
34
35#include "imfs.h"
36
37/* XXX this structure should be in an IMFS specific file */
38/* XXX this structure should use real constants */
39
40rtems_filesystem_limits_and_options_t IMFS_LIMITS_AND_OPTIONS = {
41   5,   /* link_max */
42   6,   /* max_canon */
43   7,   /* max_input */
44   IMFS_NAME_MAX,       /* name_max */
45   255, /* path_max */
46   2,   /* pipe_buf */
47   1,   /* posix_async_io */
48   2,   /* posix_chown_restrictions */
49   3,   /* posix_no_trunc */
50   4,   /* posix_prio_io */
51   5,   /* posix_sync_io */
52   6    /* posix_vdisable */
53};
54
55/*
56 *  XXX
57 */
58
59int search_mt_for_mount_point(
60  rtems_filesystem_location_info_t *location_of_mount_point
61);
62
63int init_fs_mount_table( void );
64
65
66/*
67 *  XXX
68 */
69
70#define FOUND      0
71#define NOT_FOUND -1
72
73/*
74 *  mount
75 *
76 *  This routine will attempt to mount a new file system at the specified
77 *  mount point. A series of tests will be run to determine if any of the
78 *  following reasons exist to prevent the mount operation:
79 *
80 *      1) The file system type or options are not valid
81 *      2) No new file system root node is specified
82 *      3) The selected file system has already been mounted
83 *      4) The mount point exists with the proper permissions to allow mounting
84 *      5) The selected mount point already has a file system mounted to it
85 *
86 */
87
88int mount(
89  rtems_filesystem_mount_table_entry_t **mt_entry,
90  rtems_filesystem_operations_table    *fs_ops,
91  rtems_filesystem_options_t            options,
92  char                                 *device,
93  char                                 *mount_point
94)
95{
96  rtems_filesystem_location_info_t      loc;
97  rtems_filesystem_mount_table_entry_t *temp_mt_entry;
98  rtems_filesystem_location_info_t     *loc_to_free = NULL;
99
100/* XXX add code to check for required operations */
101
102  /*
103   *  Is there a file system operations table?
104   */
105
106  if ( fs_ops == NULL ) {
107    errno = EINVAL;
108    return -1;
109  }
110
111  /*
112   *  Are the file system options valid?
113   */
114
115  if ( options != RTEMS_FILESYSTEM_READ_ONLY &&
116       options != RTEMS_FILESYSTEM_READ_WRITE ) {
117    errno = EINVAL;
118    return -1;
119  }
120
121  /*
122   * Allocate a mount table entry
123   */
124
125   temp_mt_entry = malloc( sizeof(rtems_filesystem_mount_table_entry_t) );
126
127   if ( !temp_mt_entry ) {
128     errno = ENOMEM;
129     return -1;
130   }
131
132   temp_mt_entry->mt_fs_root.mt_entry = temp_mt_entry;
133   temp_mt_entry->options = options;
134   if ( device )
135     strcpy( temp_mt_entry->dev, device );
136   else
137     temp_mt_entry->dev = 0;
138
139  /*
140   *  The mount_point should be a directory with read/write/execute
141   *  permissions in the existing tree.
142   */
143
144  if ( mount_point ) {
145
146    if ( rtems_filesystem_evaluate_path(
147            mount_point, RTEMS_LIBIO_PERMS_RWX, &loc, TRUE ) == -1 )
148      goto cleanup_and_bail;
149
150    /*
151     *  Test to see if it is a directory
152     */
153
154    loc_to_free = &loc;
155    if ( loc.ops->node_type( &loc ) != RTEMS_FILESYSTEM_DIRECTORY ) {
156      errno = ENOTDIR;
157      goto cleanup_and_bail;
158    }
159
160    /*
161     *  You can only mount one file system onto a single mount point.
162     */
163
164    if ( search_mt_for_mount_point( &loc ) == FOUND ) {
165      errno = EBUSY;
166      goto cleanup_and_bail;
167    }
168 
169    /*
170     *  This must be a good mount point, so move the location information
171     *  into the allocated mount entry.  Note:  the information that
172     *  may have been allocated in loc should not be sent to freenode
173     *  until the system is unmounted.  It may be needed to correctly
174     *  traverse the tree.
175     */
176
177    temp_mt_entry->mt_point_node.node_access = loc.node_access;
178    temp_mt_entry->mt_point_node.handlers = loc.handlers;
179    temp_mt_entry->mt_point_node.ops = loc.ops;
180    temp_mt_entry->mt_point_node.mt_entry = loc.mt_entry;
181
182    /*
183     *  This link to the parent is only done when we are dealing with system
184     *  below the base file system
185     */
186
187    if ( !loc.ops->mount ){
188      errno = ENOTSUP;
189      goto cleanup_and_bail;
190    }
191
192    if ( loc.ops->mount( temp_mt_entry ) ) {
193      goto cleanup_and_bail;
194    }
195  } else {
196
197    /*
198     *  This is a mount of the base file system --> The
199     *  mt_point_node.node_access will be set to null to indicate that this
200     *  is the root of the entire file system.
201     */
202
203    temp_mt_entry->mt_fs_root.node_access = NULL;
204    temp_mt_entry->mt_fs_root.handlers = NULL;
205    temp_mt_entry->mt_fs_root.ops = NULL;
206
207    temp_mt_entry->mt_point_node.node_access = NULL;
208    temp_mt_entry->mt_point_node.handlers = NULL;
209    temp_mt_entry->mt_point_node.ops = NULL;
210    temp_mt_entry->mt_point_node.mt_entry = NULL;
211  }
212
213  if ( !fs_ops->fsmount_me ){
214    errno = ENOTSUP;
215    goto cleanup_and_bail;
216  }
217
218  if ( fs_ops->fsmount_me( temp_mt_entry ) )
219    goto cleanup_and_bail;
220
221  /*
222   *  Add the mount table entry to the mount table chain
223   */
224
225  Chain_Append( &rtems_filesystem_mount_table_control, &temp_mt_entry->Node );
226
227  *mt_entry = temp_mt_entry;
228
229  return 0;
230
231cleanup_and_bail:
232
233  free( temp_mt_entry );
234 
235  if ( loc_to_free )
236    rtems_filesystem_freenode( loc_to_free );
237
238  return -1;
239}
240
241
242
243/*
244 *  init_fs_mount_table
245 *
246 *  This routine will initialize the chain control element that manages the
247 *  mount table chain.
248 */
249
250int init_fs_mount_table()
251{
252  Chain_Initialize_empty ( &rtems_filesystem_mount_table_control );
253  return 0;
254}
255
256
257/*
258 *  search_mt_for_mount_point
259 *
260 *  This routine will run through the entries that currently exist in the
261 *  mount table chain. For each entry in the mount table chain it will
262 *  compare the mount tables mt_point_node to the node describing the selected
263 *  mount point.. If any of the mount table file system mount point nodes
264 *  match the new file system selected mount point node, we are attempting
265 *  to mount the new file system onto a node that already has a file system
266 *  mounted to it. This is not a permitted operation.
267 */
268
269int search_mt_for_mount_point(
270  rtems_filesystem_location_info_t *location_of_mount_point
271)
272{
273  Chain_Node                           *the_node;
274  rtems_filesystem_mount_table_entry_t *the_mount_entry;
275
276  for ( the_node = rtems_filesystem_mount_table_control.first;
277        !Chain_Is_tail( &rtems_filesystem_mount_table_control, the_node );
278        the_node = the_node->next ) {
279
280     the_mount_entry = (rtems_filesystem_mount_table_entry_t *) the_node;
281     if ( the_mount_entry->mt_point_node.node_access  ==
282             location_of_mount_point->node_access )
283        return FOUND;
284  }
285  return NOT_FOUND;
286}
287
Note: See TracBrowser for help on using the repository browser.