• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /****************************************************************************
2  * fs/dirent/fs_closedir.c
3  *
4  * Copyright (c) 2023 Huawei Device Co., Ltd. All rights reserved.
5  * Based on NuttX originally from nuttx source (nuttx/fs/ and nuttx/drivers/)
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *     http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  ****************************************************************************/
20 
21 /****************************************************************************
22  * Included Files
23  ****************************************************************************/
24 
25 #include "vfs_config.h"
26 #include "dirent.h"
27 #include "errno.h"
28 #include "stdlib.h"
29 #include "fs/dirent_fs.h"
30 #include "vnode.h"
31 
32 /****************************************************************************
33  * Public Functions
34  ****************************************************************************/
35 
36 /****************************************************************************
37  * Name: closedir
38  *
39  * Description:
40  *    The closedir() function closes the directory stream associated with
41  *    'dirp'.  The directory stream descriptor 'dirp' is not available after
42  *    this call.
43  *
44  * Input Parameters:
45  *   dirp -- An instance of type DIR created by a previous call to opendir();
46  *
47  * Returned Value:
48  *   The closedir() function returns 0 on success.  On error, -1 is
49  *   returned, and errno is set appropriately.
50  *
51  ****************************************************************************/
52 
closedir(DIR * dirp)53 int closedir(DIR *dirp)
54 {
55   struct fs_dirent_s *idir = (struct fs_dirent_s *)dirp;
56   struct Vnode *vnode = NULL;
57   int ret;
58 
59   /* Verify that we were provided with a valid directory structure */
60 
61   if (!idir || idir->fd_status != DIRENT_MAGIC)
62     {
63       ret = -EBADF;
64       goto errout;
65     }
66 
67   if (idir->fd_root)
68     {
69       /* This is the 'root' vnode of the directory.  This means different
70        * things wih different filesystems.
71        */
72       vnode = idir->fd_root;
73       /* Perform the closedir() operation */
74       if (vnode->vop && vnode->vop->Closedir)
75         {
76           ret = vnode->vop->Closedir(vnode, idir);
77           if (ret < 0)
78             {
79               goto errout_with_vnode;
80             }
81         }
82       else
83         {
84           ret = -ENOSYS;
85           goto errout_with_vnode;
86         }
87       VnodeHold();
88       vnode->useCount--;
89       VnodeDrop();
90     }
91 
92   /* Then release the container */
93 
94   idir->fd_status = 0;
95   free(idir);
96 
97   return OK;
98 
99 errout_with_vnode:
100   free(idir);
101 
102 errout:
103   set_errno(-ret);
104   return VFS_ERROR;
105 }
106