xref: /third_party/NuttX/fs/vfs/fs_dup.c (revision beacf11b)
1/****************************************************************************
2 * fs/vfs/fs_dup.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
27#include "errno.h"
28#include "unistd.h"
29#include "sched.h"
30
31#include "vnode.h"
32#if defined(LOSCFG_NET_LWIP_SACK)
33#include "lwip/sockets.h"
34#endif
35
36/****************************************************************************
37 * Public Functions
38 ****************************************************************************/
39
40/****************************************************************************
41 * Name: dup
42 *
43 * Description:
44 *   Clone a file or socket descriptor to an arbitray descriptor number
45 *
46 ****************************************************************************/
47
48int dup(int fd)
49{
50  int ret = OK;
51
52  /* Check the range of the descriptor to see if we got a file or a socket
53   * descriptor.
54   */
55
56#if CONFIG_NFILE_DESCRIPTORS > 0
57  if ((unsigned int)fd < CONFIG_NFILE_DESCRIPTORS)
58    {
59      /* 0,1,2 fd is not opened in system, no need to dup them, return fd directly */
60
61      if ((fd >= STDIN_FILENO) && (fd <= STDERR_FILENO))
62        {
63          return fd;
64        }
65
66      /* Its a valid file descriptor.. dup the file descriptor using any
67       * other file descriptor.  fd_dupfd() sets the errno value in the
68       * event of any failures.
69       */
70
71      ret = fs_dupfd(fd, 3); /* 3: file start fd */
72    }
73  else
74#endif
75    {
76      /* Not a valid file descriptor.  Did we get a valid socket descriptor? */
77#if defined(LOSCFG_NET_LWIP_SACK)
78      if ((unsigned int)fd < (unsigned int)(CONFIG_NFILE_DESCRIPTORS+CONFIG_NSOCKET_DESCRIPTORS))
79        {
80          /* Yes.. dup the socket descriptor.  The errno value is not set. */
81
82          set_errno(EBADF); /* When net_dupsd is still closed,errno should set */
83          ret = VFS_ERROR;
84
85        }
86      else
87#endif
88        {
89          /* No.. then it is a bad descriptor number */
90
91          set_errno(EBADF);
92          ret = VFS_ERROR;
93        }
94    }
95
96  return ret;
97}
98