source: rtems/cpukit/libfs/src/imfs/imfs.h @ 98e5c95

4.115
Last change on this file since 98e5c95 was 98e5c95, checked in by Sebastian Huber <sebastian.huber@…>, on Dec 11, 2013 at 8:39:09 AM

PR2160: imfs: Use ENOSYS for unsupported nodes

Return an error status with errno set to ENOSYS during node creation for
nodes not available in the current configuration.

  • Property mode set to 100644
File size: 24.8 KB
Line 
1/**
2 * @file
3 *
4 * @brief Header File for the In-Memory File System
5 */
6
7/*
8 *  COPYRIGHT (c) 1989-2011.
9 *  On-Line Applications Research Corporation (OAR).
10 *
11 *  The license and distribution terms for this file may be
12 *  found in the file LICENSE in this distribution or at
13 *  http://www.rtems.com/license/LICENSE.
14 */
15
16#ifndef _RTEMS_IMFS_H
17#define _RTEMS_IMFS_H
18
19#include <limits.h>
20
21#include <rtems/libio_.h>
22#include <rtems/pipe.h>
23
24/**
25 * @brief In-Memory File System Support.
26 *
27 * @defgroup IMFS In-Memory File System Support
28 *
29 * @ingroup FileSystemTypesAndMount
30 */
31/**@{*/
32
33#ifdef __cplusplus
34extern "C" {
35#endif
36
37/*
38 *  Data types
39 */
40
41struct IMFS_jnode_tt;
42typedef struct IMFS_jnode_tt IMFS_jnode_t;
43
44typedef struct {
45  rtems_chain_control                    Entries;
46  rtems_filesystem_mount_table_entry_t  *mt_fs;
47}  IMFS_directory_t;
48
49typedef struct {
50  rtems_device_major_number  major;
51  rtems_device_minor_number  minor;
52}  IMFS_device_t;
53
54typedef struct {
55  IMFS_jnode_t  *link_node;
56} IMFS_link_t;
57
58typedef struct {
59  char *name;
60} IMFS_sym_link_t;
61
62typedef struct {
63  pipe_control_t  *pipe;
64} IMFS_fifo_t;
65
66typedef struct {
67  void *context;
68} IMFS_generic_t;
69
70/**
71 *  IMFS "memfile" information
72 *
73 *  The data structure for the in-memory "memfiles" is based on classic UNIX.
74 *
75 *  block_ptr is a pointer to a block of IMFS_MEMFILE_BYTES_PER_BLOCK in
76 *  length which could be data or a table of pointers to blocks.
77 *
78 *  Setting IMFS_MEMFILE_BYTES_PER_BLOCK to different values has a significant
79 *  impact on the maximum file size supported as well as the amount of
80 *  memory wasted due to internal file fragmentation.  The following
81 *  is a list of maximum file sizes based on various settings
82 *
83 *  @code
84 *    max_filesize with blocks of   16 is         1,328
85 *    max_filesize with blocks of   32 is        18,656
86 *    max_filesize with blocks of   64 is       279,488
87 *    max_filesize with blocks of  128 is     4,329,344
88 *    max_filesize with blocks of  256 is    68,173,568
89 *    max_filesize with blocks of  512 is 1,082,195,456
90 *  @endcode
91 */
92#define IMFS_MEMFILE_DEFAULT_BYTES_PER_BLOCK     128
93  extern int imfs_rq_memfile_bytes_per_block;
94  extern int imfs_memfile_bytes_per_block;
95
96#define IMFS_MEMFILE_BYTES_PER_BLOCK imfs_memfile_bytes_per_block
97#define IMFS_MEMFILE_BLOCK_SLOTS \
98  (IMFS_MEMFILE_BYTES_PER_BLOCK / sizeof(void *))
99
100typedef uint8_t *block_p;
101typedef block_p *block_ptr;
102
103typedef struct {
104  off_t         size;             /* size of file in bytes */
105  block_ptr     indirect;         /* array of 128 data blocks pointers */
106  block_ptr     doubly_indirect;  /* 128 indirect blocks */
107  block_ptr     triply_indirect;  /* 128 doubly indirect blocks */
108} IMFS_memfile_t;
109
110typedef struct {
111  off_t         size;             /* size of file in bytes */
112  block_p       direct;           /* pointer to file image */
113} IMFS_linearfile_t;
114
115/*
116 *  Important block numbers for "memfiles"
117 */
118#define FIRST_INDIRECT           (0)
119#define LAST_INDIRECT            (IMFS_MEMFILE_BLOCK_SLOTS - 1)
120
121#define FIRST_DOUBLY_INDIRECT    (LAST_INDIRECT + 1)
122#define LAST_DOUBLY_INDIRECT     \
123   (LAST_INDIRECT + \
124     (IMFS_MEMFILE_BLOCK_SLOTS * IMFS_MEMFILE_BLOCK_SLOTS))
125
126#define FIRST_TRIPLY_INDIRECT    (LAST_DOUBLY_INDIRECT + 1)
127#define LAST_TRIPLY_INDIRECT \
128   (LAST_DOUBLY_INDIRECT +\
129     (IMFS_MEMFILE_BLOCK_SLOTS * \
130        IMFS_MEMFILE_BLOCK_SLOTS * IMFS_MEMFILE_BLOCK_SLOTS))
131
132#define IMFS_MEMFILE_MAXIMUM_SIZE \
133  (LAST_TRIPLY_INDIRECT * IMFS_MEMFILE_BYTES_PER_BLOCK)
134
135/*
136 *  What types of IMFS file systems entities there can be.
137 */
138typedef enum {
139  IMFS_DIRECTORY = RTEMS_FILESYSTEM_DIRECTORY,
140  IMFS_DEVICE = RTEMS_FILESYSTEM_DEVICE,
141  IMFS_HARD_LINK = RTEMS_FILESYSTEM_HARD_LINK,
142  IMFS_SYM_LINK =  RTEMS_FILESYSTEM_SYM_LINK,
143  IMFS_MEMORY_FILE = RTEMS_FILESYSTEM_MEMORY_FILE,
144  IMFS_LINEAR_FILE,
145  IMFS_FIFO,
146  IMFS_GENERIC,
147  IMFS_INVALID_NODE
148} IMFS_jnode_types_t;
149
150/* The IMFS_GENERIC does not count */
151#define IMFS_TYPE_COUNT (IMFS_FIFO + 1)
152
153typedef union {
154  IMFS_directory_t   directory;
155  IMFS_device_t      device;
156  IMFS_link_t        hard_link;
157  IMFS_sym_link_t    sym_link;
158  IMFS_memfile_t     file;
159  IMFS_linearfile_t  linearfile;
160  IMFS_fifo_t        fifo;
161  IMFS_generic_t     generic;
162} IMFS_types_union;
163
164/** @} */
165
166/**
167 * @addtogroup IMFSGenericNodes
168 */
169/**@{*/
170
171/**
172 * @brief Initializes an IMFS node.
173 *
174 * @param[in,out] node The IMFS node.
175 * @param[in] info The IMFS type information.
176 *
177 * @retval node Successful operation.
178 * @retval NULL An error occurred.  The @c errno indicates the error.  This
179 * will abort the make operation.
180 *
181 * @see IMFS_node_control, IMFS_node_initialize_default(), and
182 * IMFS_node_initialize_generic().
183 */
184typedef IMFS_jnode_t *(*IMFS_node_control_initialize)(
185  IMFS_jnode_t *node,
186  const IMFS_types_union *info
187);
188
189/**
190 * @brief Returns the node and does nothing else.
191 *
192 * @param[in,out] node The IMFS node.
193 * @param[in] info The IMFS type information.
194 *
195 * @retval node Returns always the node passed as parameter.
196 *
197 * @see IMFS_node_control.
198 */
199IMFS_jnode_t *IMFS_node_initialize_default(
200  IMFS_jnode_t *node,
201  const IMFS_types_union *info
202);
203
204/**
205 * @brief Returns the node and sets the generic node context.
206 *
207 * @param[in,out] node The IMFS node.
208 * @param[in] info The IMFS type information.
209 *
210 * @retval node Returns always the node passed as parameter.
211 *
212 * @see IMFS_node_control.
213 */
214IMFS_jnode_t *IMFS_node_initialize_generic(
215  IMFS_jnode_t *node,
216  const IMFS_types_union *info
217);
218
219/**
220 * @brief Prepares the removal of an IMFS node from its parent directory.
221 *
222 * @param[in,out] node The IMFS node.
223 *
224 * @retval node Successful operation.
225 * @retval NULL An error occurred.  The @c errno indicates the error.  This
226 * will abort the removal operation.
227 *
228 * @see IMFS_node_control and IMFS_node_remove_default().
229 */
230typedef IMFS_jnode_t *(*IMFS_node_control_remove)(
231  IMFS_jnode_t *node
232);
233
234/**
235 * @brief Returns the node and does nothing else.
236 *
237 * @param[in,out] node The IMFS node.
238 *
239 * @retval node Returns always the node passed as parameter.
240 *
241 * @see IMFS_node_control.
242 */
243IMFS_jnode_t *IMFS_node_remove_default(
244  IMFS_jnode_t *node
245);
246
247/**
248 * @brief Destroys an IMFS node.
249 *
250 * @param[in,out] node The IMFS node.
251 *
252 * @retval node Returns always the node passed as parameter.
253 *
254 * @see IMFS_node_control and IMFS_node_destroy_default().
255 */
256typedef IMFS_jnode_t *(*IMFS_node_control_destroy)( IMFS_jnode_t *node );
257
258/**
259 * @brief Returns the node and does nothing else.
260 *
261 * @param[in,out] node The IMFS node.
262 *
263 * @retval node Returns always the node passed as parameter.
264 *
265 * @see IMFS_node_control.
266 */
267IMFS_jnode_t *IMFS_node_destroy_default( IMFS_jnode_t *node );
268
269/**
270 * @brief IMFS node control.
271 */
272typedef struct {
273  IMFS_jnode_types_t imfs_type;
274  const rtems_filesystem_file_handlers_r *handlers;
275  IMFS_node_control_initialize node_initialize;
276  IMFS_node_control_remove node_remove;
277  IMFS_node_control_destroy node_destroy;
278} IMFS_node_control;
279
280/** @} */
281
282/**
283 * @addtogroup IMFS
284 */
285/**@{*/
286
287/*
288 * Major device number for the IMFS. This is not a real device number because
289 * the IMFS is just a file system and does not have a driver.
290 */
291#define IMFS_DEVICE_MAJOR_NUMBER (0xfffe)
292
293/**
294 * @ingroup IMFSGenericNodes
295 *
296 * @brief Generic IMFS device major number.
297 */
298#define IMFS_GENERIC_DEVICE_MAJOR_NUMBER (0xfffd)
299
300/*
301 *  Maximum length of a "basename" of an IMFS file/node.
302 */
303
304#define IMFS_NAME_MAX  32
305
306/*
307 *  The control structure for an IMFS jnode.
308 */
309
310struct IMFS_jnode_tt {
311  rtems_chain_node    Node;                  /* for chaining them together */
312  IMFS_jnode_t       *Parent;                /* Parent node */
313  char                name[IMFS_NAME_MAX+1]; /* "basename" */
314  mode_t              st_mode;               /* File mode */
315  unsigned short      reference_count;
316  nlink_t             st_nlink;              /* Link count */
317  ino_t               st_ino;                /* inode */
318
319  uid_t               st_uid;                /* User ID of owner */
320  gid_t               st_gid;                /* Group ID of owner */
321
322  time_t              stat_atime;            /* Time of last access */
323  time_t              stat_mtime;            /* Time of last modification */
324  time_t              stat_ctime;            /* Time of last status change */
325  const IMFS_node_control *control;
326  IMFS_types_union    info;
327};
328
329static inline void IMFS_update_atime( IMFS_jnode_t *jnode )
330{
331  struct timeval now;
332
333  gettimeofday( &now, 0 );
334
335  jnode->stat_atime = now.tv_sec;
336}
337
338static inline void IMFS_update_mtime( IMFS_jnode_t *jnode )
339{
340  struct timeval now;
341
342  gettimeofday( &now, 0 );
343
344  jnode->stat_mtime = now.tv_sec;
345}
346
347static inline void IMFS_update_ctime( IMFS_jnode_t *jnode )
348{
349  struct timeval now;
350
351  gettimeofday( &now, 0 );
352
353  jnode->stat_ctime = now.tv_sec;
354}
355
356static inline void IMFS_mtime_ctime_update( IMFS_jnode_t *jnode )
357{
358  struct timeval now;
359
360  gettimeofday( &now, 0 );
361
362  jnode->stat_mtime = now.tv_sec;
363  jnode->stat_ctime = now.tv_sec;
364}
365
366typedef struct {
367  int instance;
368  ino_t ino_count;
369  const IMFS_node_control *node_controls [IMFS_TYPE_COUNT];
370} IMFS_fs_info_t;
371
372/*
373 *  Shared Data
374 */
375
376extern const IMFS_node_control IMFS_node_control_directory;
377extern const IMFS_node_control IMFS_node_control_device;
378extern const IMFS_node_control IMFS_node_control_hard_link;
379extern const IMFS_node_control IMFS_node_control_sym_link;
380extern const IMFS_node_control IMFS_node_control_memfile;
381extern const IMFS_node_control IMFS_node_control_linfile;
382extern const IMFS_node_control IMFS_node_control_fifo;
383extern const IMFS_node_control IMFS_node_control_enosys;
384
385extern const rtems_filesystem_operations_table miniIMFS_ops;
386extern const rtems_filesystem_operations_table IMFS_ops;
387extern const rtems_filesystem_operations_table fifoIMFS_ops;
388
389extern const rtems_filesystem_limits_and_options_t  IMFS_LIMITS_AND_OPTIONS;
390
391/*
392 *  Routines
393 */
394
395extern int IMFS_initialize(
396   rtems_filesystem_mount_table_entry_t *mt_entry,
397   const void                           *data
398);
399
400extern int fifoIMFS_initialize(
401  rtems_filesystem_mount_table_entry_t  *mt_entry,
402  const void                            *data
403);
404
405extern int miniIMFS_initialize(
406   rtems_filesystem_mount_table_entry_t *mt_entry,
407   const void                           *data
408);
409
410/**
411 * @brief IMFS initialization support.
412 */
413extern int IMFS_initialize_support(
414  rtems_filesystem_mount_table_entry_t *mt_entry,
415  const rtems_filesystem_operations_table *op_table,
416  const IMFS_node_control *const node_controls [IMFS_TYPE_COUNT]
417);
418/**
419 * @brief Unmount this instance of IMFS.
420 */
421extern void IMFS_fsunmount(
422   rtems_filesystem_mount_table_entry_t *mt_entry
423);
424
425/**
426 * @brief RTEMS load tarfs.
427 *
428 * This file implements the "mount" procedure for tar-based IMFS
429 * extensions.  The TAR is not actually mounted under the IMFS.
430 * Directories from the TAR file are created as usual in the IMFS.
431 * File entries are created as IMFS_LINEAR_FILE nodes with their nods
432 * pointing to addresses in the TAR image.
433 *
434 * Here we create the mountpoint directory and load the tarfs at
435 * that node.  Once the IMFS has been mounted, we work through the
436 * tar image and perform as follows:
437 *  - For directories, simply call mkdir().  The IMFS creates nodes as
438 *    needed.
439 *  - For files, we make our own calls to IMFS eval_for_make and
440 *    create_node.
441 *
442 * TAR file format:
443 *
444 * @code
445 *   Offset   Length                 Contents
446 *     0    100  bytes  File name ('\0' terminated, 99 maxmum length)
447 *   100      8  bytes  File mode (in octal ascii)
448 *   108      8  bytes  User ID (in octal ascii)
449 *   116      8  bytes  Group ID (in octal ascii)
450 *   124     12  bytes  File size (s) (in octal ascii)
451 *   136     12  bytes  Modify time (in octal ascii)
452 *   148      8  bytes  Header checksum (in octal ascii)
453 *   156      1  bytes  Link flag
454 *   157    100  bytes  Linkname ('\0' terminated, 99 maxmum length)
455 *   257      8  bytes  Magic PAX ("ustar\0" + 2 bytes padding)
456 *   257      8  bytes  Magic GNU tar ("ustar  \0")
457 *   265     32  bytes  User name ('\0' terminated, 31 maxmum length)
458 *   297     32  bytes  Group name ('\0' terminated, 31 maxmum length)
459 *   329      8  bytes  Major device ID (in octal ascii)
460 *   337      8  bytes  Minor device ID (in octal ascii)
461 *   345    167  bytes  Padding
462 *   512   (s+p) bytes  File contents (s+p) := (((s) + 511) & ~511),
463 *                      round up to 512 bytes
464 * @endcode
465 *
466 *  Checksum:
467 *  @code
468 *    int   i, sum;
469 *    char *header = tar_header_pointer;
470 *
471 *    sum = 0;
472 *    for (i = 0; i < 512; i++)
473 *        sum += 0xFF & header[i];
474 * @endcode
475 */
476extern int rtems_tarfs_load(
477   const char *mountpoint,
478   uint8_t *tar_image,
479   size_t tar_size
480);
481
482/**
483 * @brief Dump the entire IMFS.
484 *
485 * This routine dumps the entire IMFS that is mounted at the root
486 * directory.
487 *
488 * NOTE: Assuming the "/" directory is bad.
489 *       Not checking that the starting directory is in an IMFS is bad.
490 */
491extern void IMFS_dump( void );
492
493/**
494 * @brief Get the size of the largest file which can be created
495 * using the IMFS memory file type.
496 *
497 * Return the size of the largest file which can be created
498 * using the IMFS memory file type.
499 */
500extern int IMFS_memfile_maximum_size( void );
501
502/**
503 * @brief Destroy an IMFS node.
504 */
505extern void IMFS_node_destroy( IMFS_jnode_t *node );
506
507/**
508 * @brief Clone an IMFS node.
509 */
510extern int IMFS_node_clone( rtems_filesystem_location_info_t *loc );
511
512/**
513 * @brief Free an IMFS node.
514 */
515extern void IMFS_node_free( const rtems_filesystem_location_info_t *loc );
516
517/**
518 * @brief IMFS Node Type Get the type of an IMFS node.
519 *
520 * The following verifies that returns the type of node that the
521 * loc refers to.
522 */
523extern rtems_filesystem_node_types_t IMFS_node_type(
524  const rtems_filesystem_location_info_t *loc
525);
526
527/**
528 * @brief Perform a status processing for the IMFS.
529 *
530 * This routine provides a stat for the IMFS file system.
531 */
532extern int IMFS_stat(
533  const rtems_filesystem_location_info_t *loc,
534  struct stat *buf
535);
536
537/**
538 * @brief IMFS evaluation node support.
539 */
540extern void IMFS_eval_path(
541  rtems_filesystem_eval_path_context_t *ctx
542);
543
544/**
545 * @brief Create a new IMFS link node.
546 *
547 * The following rouine creates a new link node under parent with the
548 * name given in name.  The link node is set to point to the node at
549 * to_loc.
550 */
551extern int IMFS_link(
552  const rtems_filesystem_location_info_t *parentloc,
553  const rtems_filesystem_location_info_t *targetloc,
554  const char *name,
555  size_t namelen
556);
557
558/**
559 * @brief Change the owner of IMFS.
560 *
561 * This routine is the implementation of the chown() system
562 * call for the IMFS.
563 */
564extern int IMFS_chown(
565  const rtems_filesystem_location_info_t *loc,
566  uid_t owner,
567  gid_t group
568);
569
570/**
571 * @brief Create an IMFS node.
572 *
573 * Routine to create a node in the IMFS file system.
574 */
575extern int IMFS_mknod(
576  const rtems_filesystem_location_info_t *parentloc,
577  const char *name,
578  size_t namelen,
579  mode_t mode,
580  dev_t dev
581);
582
583/**
584 * @brief Create a new IMFS node.
585 *
586 * Routine to create a new in memory file system node.
587 */
588extern IMFS_jnode_t *IMFS_allocate_node(
589  IMFS_fs_info_t *fs_info,
590  const IMFS_node_control *node_control,
591  const char *name,
592  size_t namelen,
593  mode_t mode,
594  const IMFS_types_union *info
595);
596
597/**
598 * @brief Create an IMFS node.
599 *
600 * Create an IMFS filesystem node of an arbitrary type that is NOT
601 * the root directory node.
602 */
603extern IMFS_jnode_t *IMFS_create_node_with_control(
604  const rtems_filesystem_location_info_t *parentloc,
605  const IMFS_node_control *node_control,
606  const char *name,
607  size_t namelen,
608  mode_t mode,
609  const IMFS_types_union *info
610);
611
612extern bool IMFS_is_imfs_instance(
613  const rtems_filesystem_location_info_t *loc
614);
615
616/** @} */
617
618/**
619 * @defgroup IMFSGenericNodes IMFS Generic Nodes
620 *
621 * @ingroup LibIO
622 *
623 * @brief Generic nodes are an alternative to standard drivers in RTEMS.
624 *
625 * The handlers of a generic node are called with less overhead compared to the
626 * standard driver operations.  The usage of file system node handlers enable
627 * more features like support for fsync() and fdatasync().  The generic nodes
628 * use the reference counting of the IMFS.  This provides automatic node
629 * destruction when the last reference vanishes.
630 */
631/**@{*/
632
633/**
634 * @brief Makes a generic IMFS node.
635 *
636 * @param[in] path The path to the new generic IMFS node.
637 * @param[in] mode The node mode.
638 * @param[in] node_control The node control.
639 * @param[in] context The node control handler context.
640 *
641 * @retval 0 Successful operation.
642 * @retval -1 An error occurred.  The @c errno indicates the error.
643 *
644 * @code
645 * #include <sys/stat.h>
646 * #include <assert.h>
647 * #include <fcntl.h>
648 *
649 * #include <rtems/imfs.h>
650 *
651 * static const IMFS_node_control some_node_control = {
652 *   .imfs_type = IMFS_GENERIC,
653 *   .handlers = &some_node_handlers,
654 *   .node_initialize = IMFS_node_initialize_generic,
655 *   .node_remove = IMFS_node_remove_default,
656 *   .node_destroy = some_node_destroy
657 * };
658 *
659 * void example(void *some_node_context)
660 * {
661 *   int rv;
662 *
663 *   rv = IMFS_make_generic_node(
664 *     "/path/to/some/generic/node",
665 *     S_IFCHR | S_IRWXU | S_IRWXG | S_IRWXO,
666 *     &some_node_control,
667 *     some_node_context
668 *   );
669 *   assert(rv == 0);
670 * }
671 * @endcode
672 */
673extern int IMFS_make_generic_node(
674  const char *path,
675  mode_t mode,
676  const IMFS_node_control *node_control,
677  void *context
678);
679
680/** @} */
681
682/**
683 * @addtogroup IMFS
684 */
685/**@{*/
686
687/**
688 * @brief Mount an IMFS.
689 */
690extern int IMFS_mount(
691  rtems_filesystem_mount_table_entry_t *mt_entry  /* IN */
692);
693
694/**
695 * @brief Unmount an IMFS.
696 */
697extern int IMFS_unmount(
698  rtems_filesystem_mount_table_entry_t *mt_entry  /* IN */
699);
700
701extern IMFS_jnode_t *IMFS_memfile_remove(
702 IMFS_jnode_t  *the_jnode         /* IN/OUT */
703);
704
705/**
706 * @brief Truncate a memory file.
707 *
708 * This routine processes the ftruncate() system call.
709 */
710extern int memfile_ftruncate(
711  rtems_libio_t *iop,               /* IN  */
712  off_t          length             /* IN  */
713);
714
715/**
716 * @brief Read the next directory of the IMFS.
717 *
718 * This routine will read the next directory entry based on the directory
719 * offset. The offset should be equal to -n- time the size of an individual
720 * dirent structure. If n is not an integer multiple of the sizeof a
721 * dirent structure, an integer division will be performed to determine
722 * directory entry that will be returned in the buffer. Count should reflect
723 * -m- times the sizeof dirent bytes to be placed in the buffer.
724 * If there are not -m- dirent elements from the current directory position
725 * to the end of the exisiting file, the remaining entries will be placed in
726 * the buffer and the returned value will be equal to -m actual- times the
727 * size of a directory entry.
728 */
729extern ssize_t imfs_dir_read(
730  rtems_libio_t *iop,              /* IN  */
731  void          *buffer,           /* IN  */
732  size_t         count             /* IN  */
733);
734
735/**
736 * @name IMFS Memory File Handlers
737 *
738 * This section contains the set of handlers used to process operations on
739 * IMFS memory file nodes.  The memory files are created in memory using
740 * malloc'ed memory.  Thus any data stored in one of these files is lost
741 * at system shutdown unless special arrangements to copy the data to
742 * some type of non-volailte storage are made by the application.
743 */
744/**@{*/
745
746/**
747 * @brief Open a memory file.
748 *
749 * This routine processes the open() system call.  Note that there is
750 * nothing special to be done at open() time.
751 */
752extern int memfile_open(
753  rtems_libio_t *iop,             /* IN  */
754  const char    *pathname,        /* IN  */
755  int            oflag,           /* IN  */
756  mode_t         mode             /* IN  */
757);
758
759/**
760 * @brief Read a memory file.
761 *
762 * This routine processes the read() system call.
763 */
764extern ssize_t memfile_read(
765  rtems_libio_t *iop,             /* IN  */
766  void          *buffer,          /* IN  */
767  size_t         count            /* IN  */
768);
769
770/**
771 * @brief Write a memory file.
772 *
773 * This routine processes the write() system call.
774 */
775extern ssize_t memfile_write(
776  rtems_libio_t *iop,             /* IN  */
777  const void    *buffer,          /* IN  */
778  size_t         count            /* IN  */
779);
780
781/** @} */
782
783/**
784 * @name IMFS Device Node Handlers
785 *
786 * This section contains the set of handlers used to map operations on
787 * IMFS device nodes onto calls to the RTEMS Classic API IO Manager.
788 */
789/**@{*/
790
791extern int device_open(
792  rtems_libio_t *iop,            /* IN  */
793  const char    *pathname,       /* IN  */
794  int            oflag,          /* IN  */
795  mode_t         mode            /* IN  */
796);
797
798extern int device_close(
799  rtems_libio_t *iop             /* IN  */
800);
801
802extern ssize_t device_read(
803  rtems_libio_t *iop,            /* IN  */
804  void          *buffer,         /* IN  */
805  size_t         count           /* IN  */
806);
807
808extern ssize_t device_write(
809  rtems_libio_t *iop,               /* IN  */
810  const void    *buffer,            /* IN  */
811  size_t         count              /* IN  */
812);
813
814extern int device_ioctl(
815  rtems_libio_t   *iop,
816  ioctl_command_t  command,
817  void            *buffer
818);
819
820extern int device_ftruncate(
821  rtems_libio_t *iop,               /* IN  */
822  off_t          length             /* IN  */
823);
824
825/** @} */
826
827/**
828 * @brief Set IMFS file access and modification times.
829 *
830 *
831 * This routine is the implementation of the utime() system
832 * call for the IMFS.
833 */
834extern int IMFS_utime(
835  const rtems_filesystem_location_info_t *loc,
836  time_t actime,
837  time_t modtime
838);
839
840/**
841 * @brief Change the IMFS file mode.
842 */
843extern int IMFS_fchmod(
844  const rtems_filesystem_location_info_t *loc,
845  mode_t mode
846);
847
848/**
849 * @brief Create a new IMFS symbolic link node.
850 *
851 * The following rouine creates a new symbolic link node under parent
852 * with the name given in name.  The node is set to point to the node at
853 * to_loc.
854 */
855extern int IMFS_symlink(
856  const rtems_filesystem_location_info_t *parentloc,
857  const char *name,
858  size_t namelen,
859  const char *target
860);
861
862/**
863 * @brief Put IMFS symbolic link into buffer.
864 *
865 * The following rouine puts the symbolic links destination name into
866 * buff.
867 *
868 */
869extern ssize_t IMFS_readlink(
870  const rtems_filesystem_location_info_t *loc,
871  char *buf,
872  size_t bufsize
873);
874
875/**
876 * @brief Rename the IMFS.
877 *
878 * The following rouine creates a new link node under parent with the
879 * name given in name and removes the old.
880 */
881extern int IMFS_rename(
882  const rtems_filesystem_location_info_t *oldparentloc,
883  const rtems_filesystem_location_info_t *oldloc,
884  const rtems_filesystem_location_info_t *newparentloc,
885  const char *name,
886  size_t namelen
887);
888/**
889 * @brief IMFS node removal handler.
890 *
891 * This file contains the handler used to remove a node when a file type
892 * does not require special actions.
893 */
894extern int IMFS_rmnod(
895  const rtems_filesystem_location_info_t *parentloc,
896  const rtems_filesystem_location_info_t *loc
897);
898
899/*
900 *  Turn on IMFS assertions when RTEMS_DEBUG is defined.
901 */
902#ifdef RTEMS_DEBUG
903  #include <assert.h>
904
905  #define IMFS_assert(_x) assert(_x)
906#else
907  #define IMFS_assert(_x)
908#endif
909
910static inline void IMFS_Set_handlers( rtems_filesystem_location_info_t *loc )
911{
912  IMFS_jnode_t *node = (IMFS_jnode_t *) loc->node_access;
913
914  loc->handlers = node->control->handlers;
915}
916
917static inline void IMFS_add_to_directory(
918  IMFS_jnode_t *dir,
919  IMFS_jnode_t *node
920)
921{
922  node->Parent = dir;
923  rtems_chain_append_unprotected( &dir->info.directory.Entries, &node->Node );
924}
925
926static inline void IMFS_remove_from_directory( IMFS_jnode_t *node )
927{
928  IMFS_assert( node->Parent != NULL );
929  node->Parent = NULL;
930  rtems_chain_extract_unprotected( &node->Node );
931}
932
933static inline IMFS_jnode_types_t IMFS_type( const IMFS_jnode_t *node )
934{
935  return node->control->imfs_type;
936}
937
938static inline bool IMFS_is_directory( const IMFS_jnode_t *node )
939{
940  return node->control->imfs_type == IMFS_DIRECTORY;
941}
942
943static inline IMFS_jnode_t *IMFS_create_node(
944  const rtems_filesystem_location_info_t *parentloc,
945  IMFS_jnode_types_t type,
946  const char *name,
947  size_t namelen,
948  mode_t mode,
949  const IMFS_types_union *info
950)
951{
952  const IMFS_fs_info_t *fs_info =
953    (const IMFS_fs_info_t *) parentloc->mt_entry->fs_info;
954
955  return IMFS_create_node_with_control(
956    parentloc,
957    fs_info->node_controls [type],
958    name,
959    namelen,
960    mode,
961    info
962  );
963}
964
965/** @} */
966
967/**
968 * @addtogroup IMFSGenericNodes
969 */
970/**@{*/
971
972static inline void *IMFS_generic_get_context_by_node(
973  const IMFS_jnode_t *node
974)
975{
976  return node->info.generic.context;
977}
978
979static inline void *IMFS_generic_get_context_by_location(
980  const rtems_filesystem_location_info_t *loc
981)
982{
983  const IMFS_jnode_t *node = (const IMFS_jnode_t *) loc->node_access;
984
985  return IMFS_generic_get_context_by_node( node );
986}
987
988static inline void *IMFS_generic_get_context_by_iop(
989  const rtems_libio_t *iop
990)
991{
992  return IMFS_generic_get_context_by_location( &iop->pathinfo );
993}
994
995static inline dev_t IMFS_generic_get_device_identifier_by_node(
996  const IMFS_jnode_t *node
997)
998{
999  return rtems_filesystem_make_dev_t(
1000    IMFS_GENERIC_DEVICE_MAJOR_NUMBER,
1001    node->st_ino
1002  );
1003}
1004
1005#ifdef __cplusplus
1006}
1007#endif
1008/** @} */
1009#endif
1010/* end of include file */
Note: See TracBrowser for help on using the repository browser.