VDMemDisk.cpp revision dd5eddcb518723b83065517ffce68dd63f7faad9
/** $Id$ */
/** @file
*
*/
/*
* Copyright (C) 2011 Oracle Corporation
*
* This file is part of VirtualBox Open Source Edition (OSE), as
* available from http://www.virtualbox.org. This file is free software;
* General Public License (GPL) as published by the Free Software
* Foundation, in version 2 as it comes in the "COPYING" file of the
* VirtualBox OSE distribution. VirtualBox OSE is distributed in the
* hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
*/
#include "VDMemDisk.h"
/**
*/
typedef struct VDMEMDISK
{
/** Current size of the disk. */
/** Flag whether the disk can grow. */
bool fGrowable;
/** Pointer to the AVL tree holding the segments. */
} VDMEMDISK;
/**
* A disk segment.
*/
typedef struct VDMEMDISKSEG
{
/** AVL tree core. */
/** Pointer to the data. */
void *pvSeg;
{
int rc = VINF_SUCCESS;
if (pMemDisk)
{
if (pMemDisk->pTreeSegments)
else
{
rc = VERR_NO_MEMORY;
}
}
else
rc = VERR_NO_MEMORY;
return rc;
}
{
return VINF_SUCCESS;
}
{
}
{
int rc = VINF_SUCCESS;
LogFlowFunc(("pMemDisk=%#p off=%llu cbWrite=%zu pSgBuf=%#p\n",
/* Check for a write beyond the end of a disk. */
return VERR_INVALID_PARAMETER;
/* Update the segments */
while ( cbLeft
&& RT_SUCCESS(rc))
{
unsigned offSeg = 0;
if (!pSeg)
{
/* Get next segment */
if ( !pSeg
else
/* Create new segment */
if (pSeg)
{
{
rc = VERR_NO_MEMORY;
}
else
{
}
}
else
rc = VERR_NO_MEMORY;
}
else
{
}
if (RT_SUCCESS(rc))
{
}
}
/* Update size of the disk. */
if ( RT_SUCCESS(rc)
{
}
return rc;
}
{
LogFlowFunc(("pMemDisk=%#p off=%llu cbRead=%zu pSgBuf=%#p\n",
/* Check for a read beyond the end of a disk. */
return VERR_INVALID_PARAMETER;
/* Compare read data */
while (cbLeft)
{
unsigned offSeg = 0;
if (!pSeg)
{
/* Get next segment */
if ( !pSeg
{
/* No data in the tree for this read. Fill with 0. */
}
else
}
else
{
}
}
return VINF_SUCCESS;
}
{
return VERR_NOT_SUPPORTED;
{
/* Increase. */
}
else
{
/* We have to delete all parts beyond the new end. */
if (pSeg)
{
{
/* Cut off the part which is not in the file anymore. */
}
else
{
/* Free the whole block. */
}
}
/* Kill all blocks coming after. */
do
{
if (pSeg)
{
}
else
break;
} while (true);
}
return VINF_SUCCESS;
}
{
return VINF_SUCCESS;
}
/**
* Writes a segment to the given file.
*
* @returns IPRT status code.
*
* @param pNode The disk segment to write to the file.
* @param pvParam Opaque user data containing the pointer to
* the file handle.
*/
{
return RTFileWriteAt(hFile, pSeg->Core.Key, pSeg->pvSeg, pSeg->Core.KeyLast - pSeg->Core.Key + 1, NULL);
}
{
int rc = VINF_SUCCESS;
if (RT_SUCCESS(rc))
{
if (RT_FAILURE(rc))
}
return rc;
}
{
return VERR_NOT_IMPLEMENTED;
}
{
LogFlowFunc(("pMemDisk=%#p off=%llx cbCmp=%u pSgBuf=%#p\n",
/* Compare data */
while (cbLeft)
{
bool fCmp = false;
unsigned offSeg = 0;
if (!pSeg)
{
/* Get next segment */
if (!pSeg)
{
/* No data in the tree for this read. Assume everything is ok. */
}
else
}
else
{
fCmp = true;
}
if (fCmp)
{
int rc = 0;
if (rc)
return rc;
}
else
}
return 0;
}