vfsbase.cpp revision 835ac9173220411ef9fe578c3d4c03e5edfa20be
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * IPRT - Virtual File System, Base.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Copyright (C) 2010 Oracle Corporation
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * This file is part of VirtualBox Open Source Edition (OSE), as
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * available from http://www.virtualbox.org. This file is free software;
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * you can redistribute it and/or modify it under the terms of the GNU
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * General Public License (GPL) as published by the Free Software
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Foundation, in version 2 as it comes in the "COPYING" file of the
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The contents of this file may alternatively be used under the terms
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * of the Common Development and Distribution License Version 1.0
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * VirtualBox OSE distribution, in which case the provisions of the
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * CDDL are applicable instead of those of the GPL.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * You may elect to license modified versions of this file under the
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * terms and conditions of either the GPL or the CDDL or both.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*******************************************************************************
59190ecd61435d19ba3515b876272aee7bd12298vboxsync* Header Files *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync*******************************************************************************/
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*******************************************************************************
59190ecd61435d19ba3515b876272aee7bd12298vboxsync* Defined Constants And Macros *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync*******************************************************************************/
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#define RTVFSFSSTREAM_MAGIC_DEAD (~RTVFSFSSTREAM_MAGIC)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#define RTVFSIOSTREAM_MAGIC_DEAD (~RTVFSIOSTREAM_MAGIC)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#define RTVFSSYMLINK_MAGIC_DEAD (~RTVFSSYMLINK_MAGIC)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** The instance data alignment. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** The max number of symbolic links to resolve in a path. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Asserts that the VFS base object vtable is valid. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((a_pObjOps)->uVersion == RTVFSOBJOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((a_pObjOps)->enmType == (a_enmType) || (a_enmType) == RTVFSOBJTYPE_INVALID); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((a_pObjOps)->uEndMarker == RTVFSOBJOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync } while (0)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Asserts that the VFS set object vtable is valid. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#define RTVFSOBJSET_ASSERT_OPS(a_pSetOps, a_offObjOps) \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((a_pSetOps)->uVersion == RTVFSOBJSETOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((a_pSetOps)->uEndMarker == RTVFSOBJSETOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync } while (0)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Asserts that the VFS I/O stream vtable is valid. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#define RTVFSIOSTREAM_ASSERT_OPS(pIoStreamOps, a_enmType) \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTVFSOBJ_ASSERT_OPS(&(pIoStreamOps)->Obj, a_enmType); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((pIoStreamOps)->uVersion == RTVFSIOSTREAMOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert(!((pIoStreamOps)->fFeatures & ~RTVFSIOSTREAMOPS_FEAT_VALID_MASK)); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((pIoStreamOps)->uEndMarker == RTVFSIOSTREAMOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync } while (0)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Asserts that the VFS symlink vtable is valid. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#define RTVFSSYMLINK_ASSERT_OPS(pSymlinkOps, a_enmType) \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTVFSOBJ_ASSERT_OPS(&(pSymlinkOps)->Obj, a_enmType); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RT_OFFSETOF(RTVFSSYMLINKOPS, Obj) - RT_OFFSETOF(RTVFSSYMLINKOPS, ObjSet)); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((pSymlinkOps)->uVersion == RTVFSSYMLINKOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync Assert((pSymlinkOps)->uEndMarker == RTVFSSYMLINKOPS_VERSION); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync } while (0)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** Validates a VFS handle and returns @a rcRet if it's invalid. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#define RTVFS_ASSERT_VALID_HANDLE_OR_NIL_RETURN(hVfs, rcRet) \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync AssertReturn((hVfs)->uMagic == RTVFS_MAGIC, (rcRet)); \
59190ecd61435d19ba3515b876272aee7bd12298vboxsync } while (0)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/*******************************************************************************
59190ecd61435d19ba3515b876272aee7bd12298vboxsync* Structures and Typedefs *
59190ecd61435d19ba3515b876272aee7bd12298vboxsync*******************************************************************************/
59190ecd61435d19ba3515b876272aee7bd12298vboxsync/** @todo Move all this stuff to internal/vfs.h */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS internal lock data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The number of references to the this lock. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The lock type. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Type specific data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Read/Write semaphore handle. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Fast mutex semaphore handle. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Regular mutex semaphore handle. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS base object handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * All other VFS handles are derived from this one. The final handle type is
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * indicated by RTVFSOBJOPS::enmType via the RTVFSOBJINTERNAL::pOps member.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSOBJ_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The number of references to this VFS object. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Pointer to the instance data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The lock protecting all access to the VFS.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Only valid RTVFS_C_THREAD_SAFE is set, otherwise it is NIL_RTVFSLOCK. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Reference back to the VFS containing this object. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS filesystem stream handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSOBJINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSFSTREAM_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** File open flags, at a minimum the access mask. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The base object handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSOBJINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFS_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Creation flags (RTVFS_C_XXX). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The base object handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS directory handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSOBJINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSDIR_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Reserved for flags or something. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The base object handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS symbolic link handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSOBJINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSSYMLINK_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Reserved for flags or something. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The base object handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS I/O stream handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * This is often part of a type specific handle, like a file or pipe.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSOBJINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSIOSTREAM_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** File open flags, at a minimum the access mask. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The base object handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS file handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSIOSTREAMINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSFILE_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Reserved for flags or something. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The stream handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#if 0 /* later */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS pipe handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSIOSTREAMINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSPIPE_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Reserved for flags or something. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The stream handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * The VFS socket handle data.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @extends RTVFSIOSTREAMINTERNAL
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The VFS magic (RTVFSSOCKET_MAGIC). */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** Reserved for flags or something. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The vtable. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync /** The stream handle data. */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync#endif /* later */
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * V F S L o c k A b s t r a c t i o n
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * V F S L o c k A b s t r a c t i o n
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * V F S L o c k A b s t r a c t i o n
59190ecd61435d19ba3515b876272aee7bd12298vboxsync AssertReturn(pThis->enmType > RTVFSLOCKTYPE_INVALID && pThis->enmType < RTVFSLOCKTYPE_END, UINT32_MAX);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync AssertMsg(cRefs > 1 && cRefs < _1M, ("%#x %p %d\n", cRefs, pThis, pThis->enmType));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Destroys a VFS lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param pThis The lock to destroy.
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncstatic void rtVfsLockDestroy(RTVFSLOCKINTERNAL *pThis)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync AssertMsgFailedReturnVoid(("%p %d\n", pThis, pThis->enmType));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync AssertReturn(pThis->enmType > RTVFSLOCKTYPE_INVALID && pThis->enmType < RTVFSLOCKTYPE_END, UINT32_MAX);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync AssertMsg(cRefs < _1M, ("%#x %p %d\n", cRefs, pThis, pThis->enmType));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Creates a read/write lock.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @returns IPRT status code
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param phLock Where to return the lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTVFSLOCKINTERNAL *pThis = (RTVFSLOCKINTERNAL *)RTMemAlloc(sizeof(*pThis));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Creates a fast mutex lock.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @returns IPRT status code
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param phLock Where to return the lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncstatic int rtVfsLockCreateFastMutex(PRTVFSLOCK phLock)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTVFSLOCKINTERNAL *pThis = (RTVFSLOCKINTERNAL *)RTMemAlloc(sizeof(*pThis));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Creates a mutex lock.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @returns IPRT status code
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param phLock Where to return the lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync RTVFSLOCKINTERNAL *pThis = (RTVFSLOCKINTERNAL *)RTMemAlloc(sizeof(*pThis));
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Acquires the lock for reading.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param hLock Non-nil lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @internal
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncRTDECL(void) RTVfsLockAcquireReadSlow(RTVFSLOCK hLock)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync rc = RTSemRWRequestRead(pThis->u.hSemRW, RT_INDEFINITE_WAIT);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync rc = RTSemMutexRequest(pThis->u.hMtx, RT_INDEFINITE_WAIT);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Release a lock held for reading.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param hLock Non-nil lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @internal
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncRTDECL(void) RTVfsLockReleaseReadSlow(RTVFSLOCK hLock)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Acquires the lock for writing.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param hLock Non-nil lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @internal
59190ecd61435d19ba3515b876272aee7bd12298vboxsyncRTDECL(void) RTVfsLockAcquireWriteSlow(RTVFSLOCK hLock)
59190ecd61435d19ba3515b876272aee7bd12298vboxsync rc = RTSemRWRequestWrite(pThis->u.hSemRW, RT_INDEFINITE_WAIT);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync rc = RTSemMutexRequest(pThis->u.hMtx, RT_INDEFINITE_WAIT);
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * Release a lock held for writing.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @param hLock Non-nil lock handle.
59190ecd61435d19ba3515b876272aee7bd12298vboxsync * @internal
int rc;
case RTVFSLOCKTYPE_RW:
case RTVFSLOCKTYPE_FASTMUTEX:
case RTVFSLOCKTYPE_MUTEX:
AssertFailed();
("%#x %p ops=%p %s (%d)\n", cRefs, pThis, pThis->pOps, pThis->pOps->pszName, pThis->pOps->enmType));
static int rtVfsObjInitNewObject(RTVFSOBJINTERNAL *pThis, PCRTVFSOBJOPS pObjOps, RTVFS hVfs, RTVFSLOCK hLock, void *pvThis)
int rc;
AssertReturn(hLock->enmType > RTVFSLOCKTYPE_INVALID && hLock->enmType < RTVFSLOCKTYPE_END, VERR_INVALID_HANDLE);
return VERR_INVALID_HANDLE;
return VINF_SUCCESS;
if (!pThis)
return VERR_NO_MEMORY;
return rc;
return VINF_SUCCESS;
("%#x %p ops=%p %s (%d)\n", cRefs, pThis, pThis->pOps, pThis->pOps->pszName, pThis->pOps->enmType));
return cRefs;
switch (enmType)
case RTVFSOBJTYPE_BASE:
case RTVFSOBJTYPE_VFS:
case RTVFSOBJTYPE_FS_STREAM:
ASMAtomicWriteU32(&RT_FROM_MEMBER(pThis, RTVFSFSSTREAMINTERNAL, Base)->uMagic, RTVFSFSSTREAM_MAGIC_DEAD);
case RTVFSOBJTYPE_IO_STREAM:
ASMAtomicWriteU32(&RT_FROM_MEMBER(pThis, RTVFSIOSTREAMINTERNAL, Base)->uMagic, RTVFSIOSTREAM_MAGIC_DEAD);
case RTVFSOBJTYPE_DIR:
case RTVFSOBJTYPE_FILE:
ASMAtomicWriteU32(&RT_FROM_MEMBER(pThis, RTVFSFILEINTERNAL, Stream.Base)->uMagic, RTVFSFILE_MAGIC_DEAD);
ASMAtomicWriteU32(&RT_FROM_MEMBER(pThis, RTVFSIOSTREAMINTERNAL, Base)->uMagic, RTVFSIOSTREAM_MAGIC_DEAD);
case RTVFSOBJTYPE_SYMLINK:
ASMAtomicWriteU32(&RT_FROM_MEMBER(pThis, RTVFSSYMLINKINTERNAL, Base)->uMagic, RTVFSSYMLINK_MAGIC_DEAD);
case RTVFSOBJTYPE_INVALID:
case RTVFSOBJTYPE_END:
case RTVFSOBJTYPE_32BIT_HACK:
AssertMsg(cRefs < _1M, ("%#x %p ops=%p %s (%d)\n", cRefs, pThis, pThis->pOps, pThis->pOps->pszName, pThis->pOps->enmType));
if (cRefs == 0)
return cRefs;
return NIL_RTVFS;
return NIL_RTVFSFSSTREAM;
return NIL_RTVFSDIR;
return NIL_RTVFSIOSTREAM;
return NIL_RTVFSFILE;
return NIL_RTVFSSYMLINK;
return pThis;
return NIL_RTVFSOBJ;
return pThis;
return NIL_RTVFSOBJ;
return pThis;
return NIL_RTVFSOBJ;
return pThis;
return NIL_RTVFSOBJ;
return pThis;
return NIL_RTVFSOBJ;
return pThis;
return NIL_RTVFSOBJ;
return rc;
static char *rtVfsParsePathHandleDots(PRTVFSPARSEDPATH pPath, char *pszDst, bool fTheEnd, uint16_t *piRestartComp)
return pszDst;
return pszDst;
pszDst--;
return pszDst;
RTDECL(int) RTVfsParsePathAppend(PRTVFSPARSEDPATH pPath, const char *pszPath, uint16_t *piRestartComp)
return VERR_FILENAME_TOO_LONG;
while (pszSrc[0])
pszSrc++;
while (pszSrc[0])
pszSrc++;
if (pszSrc[0])
return VERR_FILENAME_TOO_LONG;
return VINF_SUCCESS;
return rc;
pszPath++;
if (!pszPath[0])
return VINF_SUCCESS;
int rc;
if (pPath)
return rc;
if (pPath)
static int rtVfsTraverseHandleSymlink(PRTVFSPARSEDPATH pPath, uint16_t *piComponent, RTVFSSYMLINK hSymlink)
*piComponent = 0;
return VINF_SUCCESS;
return VINF_SUCCESS;
return rc;
unsigned cLinks = 0;
return VINF_SUCCESS;
if (fFinal)
return VINF_SUCCESS;
iComponent++;
cLinks++;
iComponent = 0;
iComponent = 0;
if (pCurDir)
return rc;
RTDECL(int) RTVfsUtilDummyPollOne(uint32_t fEvents, RTMSINTERVAL cMillies, bool fIntr, uint32_t *pfRetEvents)
int rc;
if (fIntr)
&& !fIntr
*pfRetEvents = 0;
return rc;
RTDECL(int) RTVfsUtilPumpIoStreams(RTVFSIOSTREAM hVfsIosSrc, RTVFSIOSTREAM hVfsIosDst, size_t cbBufHint)
if (!cbBuf)
if (!pvBuf)
if (!pvBuf)
return VERR_NO_TMP_MEMORY;
int rc;
return rc;
RTDECL(int) RTVfsNewFsStream(PCRTVFSFSSTREAMOPS pFsStreamOps, size_t cbInstance, RTVFS hVfs, RTVFSLOCK hLock,
if (!pThis)
return VERR_NO_MEMORY;
return rc;
return VINF_SUCCESS;
RTDECL(int) RTVfsFsStrmQueryInfo(RTVFSFSSTREAM hVfsFss, PRTFSOBJINFO pObjInfo, RTFSOBJATTRADD enmAddAttr)
RTDECL(int) RTVfsFsStrmNext(RTVFSFSSTREAM hVfsFss, char **ppszName, RTVFSOBJTYPE *penmType, PRTVFSOBJ phVfsObj)
if (ppszName)
if (penmType)
if (phVfsObj)
RTDECL(int) RTVfsNewSymlink(PCRTVFSSYMLINKOPS pSymlinkOps, size_t cbInstance, RTVFS hVfs, RTVFSLOCK hLock,
if (!pThis)
return VERR_NO_MEMORY;
return rc;
return VINF_SUCCESS;
RTDECL(int) RTVfsSymlinkQueryInfo(RTVFSSYMLINK hVfsSym, PRTFSOBJINFO pObjInfo, RTFSOBJATTRADD enmAddAttr)
return VERR_INVALID_PARAMETER;
return rc;
RTDECL(int) RTVfsSymlinkSetTimes(RTVFSSYMLINK hVfsSym, PCRTTIMESPEC pAccessTime, PCRTTIMESPEC pModificationTime,
int rc = pThis->pOps->ObjSet.pfnSetTimes(pThis->Base.pvThis, pAccessTime, pModificationTime, pChangeTime, pBirthTime);
return rc;
return rc;
return rc;
RTDECL(int) RTVfsNewIoStream(PCRTVFSIOSTREAMOPS pIoStreamOps, size_t cbInstance, uint32_t fOpen, RTVFS hVfs, RTVFSLOCK hLock,
if (!pThis)
return VERR_NO_MEMORY;
return rc;
return VINF_SUCCESS;
return NULL;
return NIL_RTVFSFILE;
RTDECL(int) RTVfsIoStrmQueryInfo(RTVFSIOSTREAM hVfsIos, PRTFSOBJINFO pObjInfo, RTFSOBJATTRADD enmAddAttr)
RTDECL(int) RTVfsIoStrmRead(RTVFSIOSTREAM hVfsIos, void *pvBuf, size_t cbToRead, bool fBlocking, size_t *pcbRead)
if (pcbRead)
*pcbRead = 0;
return rc;
RTDECL(int) RTVfsIoStrmWrite(RTVFSIOSTREAM hVfsIos, const void *pvBuf, size_t cbToWrite, bool fBlocking, size_t *pcbWritten)
if (pcbWritten)
*pcbWritten = 0;
return rc;
RTDECL(int) RTVfsIoStrmSgRead(RTVFSIOSTREAM hVfsIos, PCRTSGBUF pSgBuf, bool fBlocking, size_t *pcbRead)
if (pcbRead)
*pcbRead = 0;
int rc;
rc = pThis->pOps->pfnRead(pThis->Base.pvThis, -1 /*off*/, &SgBuf, fBlocking, pcbRead ? &cbReadSeg : NULL);
if (pcbRead)
return rc;
RTDECL(int) RTVfsIoStrmSgWrite(RTVFSIOSTREAM hVfsIos, PCRTSGBUF pSgBuf, bool fBlocking, size_t *pcbWritten)
if (pcbWritten)
*pcbWritten = 0;
int rc;
rc = pThis->pOps->pfnWrite(pThis->Base.pvThis, -1 /*off*/, &SgBuf, fBlocking, pcbWritten ? &cbWrittenSeg : NULL);
if (pcbWritten)
if (pcbWritten)
return rc;
return rc;
RTDECL(RTFOFF) RTVfsIoStrmPoll(RTVFSIOSTREAM hVfsIos, uint32_t fEvents, RTMSINTERVAL cMillies, bool fIntr,
return rc;
return off;
int rc;
if (pvBuf)
while (cb > 0)
return rc;
int rc;
if (pvBuf)
while (cb > 0)
return rc;
char bDummy;
RTDECL(int) RTVfsNewFile(PCRTVFSFILEOPS pFileOps, size_t cbInstance, uint32_t fOpen, RTVFS hVfs, RTVFSLOCK hLock,
if (!pThis)
return VERR_NO_MEMORY;
return rc;
return VINF_SUCCESS;
RTDECL(int) RTVfsFileOpen(RTVFS hVfs, const char *pszFilename, uint32_t fOpen, PRTVFSFILE phVfsFile)
return rc;
return rc;