1/**************************************************************************** 2 * fs/driver/fs_findblockdriver.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 "sys/types.h" 28#include "sys/mount.h" 29#include "errno.h" 30#include "fs/driver.h" 31#include "string.h" 32 33/**************************************************************************** 34 * Public Functions 35 ****************************************************************************/ 36 37/**************************************************************************** 38 * Name: find_blockdriver 39 * 40 * Description: 41 * Return the inode of the block driver specified by 'pathname' 42 * 43 * Input Parameters: 44 * pathname - The full path to the block driver to be located 45 * mountflags - If MS_RDONLY is not set, then driver must support write 46 * operations (see include/sys/mount.h) 47 * ppinode - Address of the location to return the inode reference 48 * 49 * Returned Value: 50 * Returns zero on success or a negated errno on failure: 51 * 52 * ENOENT - No block driver of this name is registered 53 * ENOTBLK - The inode associated with the pathname is not a block driver 54 * EACCESS - The MS_RDONLY option was not set but this driver does not 55 * support write access 56 * 57 ****************************************************************************/ 58int find_blockdriver(const char *pathname, int mountflags, struct Vnode **vpp) 59{ 60 int ret; 61 struct Vnode *vp = NULL; 62 63 /* Sanity checks */ 64 65 /* Find the vnode registered with this pathname */ 66 VnodeHold(); 67 ret = VnodeLookup(pathname, &vp, V_DUMMY); 68 if (ret < 0) 69 { 70 ret = -EACCES; 71 goto errout; 72 } 73 74 /* Verify that the vnode is a block driver. */ 75 if (vp->type != VNODE_TYPE_BLK) 76 { 77 PRINT_DEBUG("%s is not a block driver\n", pathname); 78 ret = -ENOTBLK; 79 goto errout; 80 } 81 82 /* Make sure that the vnode supports the requested access */ 83 84 struct block_operations *i_bops = (struct block_operations *)((struct drv_data *)vp->data)->ops; 85 86 if (i_bops == NULL || i_bops->read == NULL || (i_bops->write == NULL && (mountflags & MS_RDONLY) == 0)) 87 { 88 PRINT_DEBUG("%s does not support requested access\n", pathname); 89 ret = -EACCES; 90 goto errout; 91 } 92 93 *vpp = vp; 94 VnodeDrop(); 95 return OK; 96 97errout: 98 VnodeDrop(); 99 return ret; 100} 101