/** * Queries information about the object using a specific view, internal version. * * @return IPRT status code. * @param enmView View to use for querying information. Currently ignored. */ int DnDURIObject::queryInfoInternal(View enmView) { RT_NOREF(enmView); int rc; switch (m_enmType) { case Type_File: AssertMsgReturn(RTFileIsValid(u.File.hFile), ("Object has invalid file handle\n"), VERR_INVALID_STATE); rc = RTFileQueryInfo(u.File.hFile, &u.File.objInfo, RTFSOBJATTRADD_NOTHING); break; case Type_Directory: AssertMsgReturn(RTDirIsValid(u.Dir.hDir), ("Object has invalid directory handle\n"), VERR_INVALID_STATE); rc = RTDirQueryInfo(u.Dir.hDir, &u.Dir.objInfo, RTFSOBJATTRADD_NOTHING); break; default: rc = VERR_NOT_IMPLEMENTED; break; } return rc; }
/** * Returns whether the object is in an open state or not. */ bool DnDURIObject::IsOpen(void) const { switch (m_enmType) { case Type_File: return RTFileIsValid(u.File.hFile); case Type_Directory: return RTDirIsValid(u.Dir.hDir); default: break; } return false; }
RTDECL(int) RTFileCompareByHandlesEx(RTFILE hFile1, RTFILE hFile2, uint32_t fFlags, PFNRTPROGRESS pfnProgress, void *pvUser) { /* * Validate input. */ AssertReturn(RTFileIsValid(hFile1), VERR_INVALID_HANDLE); AssertReturn(RTFileIsValid(hFile1), VERR_INVALID_HANDLE); AssertMsgReturn(!pfnProgress || VALID_PTR(pfnProgress), ("pfnProgress=%p\n", pfnProgress), VERR_INVALID_PARAMETER); AssertMsgReturn(!(fFlags & ~RTFILECOMP_FLAGS_MASK), ("%#x\n", fFlags), VERR_INVALID_PARAMETER); /* * Compare the file sizes first. */ uint64_t cbFile1; int rc = RTFileGetSize(hFile1, &cbFile1); if (RT_FAILURE(rc)) return rc; uint64_t cbFile2; rc = RTFileGetSize(hFile1, &cbFile2); if (RT_FAILURE(rc)) return rc; if (cbFile1 != cbFile2) return VERR_NOT_EQUAL; /* * Allocate buffer. */ size_t cbBuf; uint8_t *pbBuf1Free = NULL; uint8_t *pbBuf1; uint8_t *pbBuf2Free = NULL; uint8_t *pbBuf2; if (cbFile1 < _512K) { cbBuf = 8*_1K; pbBuf1 = (uint8_t *)alloca(cbBuf); pbBuf2 = (uint8_t *)alloca(cbBuf); } else { cbBuf = _128K; pbBuf1 = pbBuf1Free = (uint8_t *)RTMemTmpAlloc(cbBuf); pbBuf2 = pbBuf2Free = (uint8_t *)RTMemTmpAlloc(cbBuf); } if (pbBuf1 && pbBuf2) { /* * Seek to the start of each file * and set the size of the destination file. */ rc = RTFileSeek(hFile1, 0, RTFILE_SEEK_BEGIN, NULL); if (RT_SUCCESS(rc)) { rc = RTFileSeek(hFile2, 0, RTFILE_SEEK_BEGIN, NULL); if (RT_SUCCESS(rc) && pfnProgress) rc = pfnProgress(0, pvUser); if (RT_SUCCESS(rc)) { /* * Compare loop. */ unsigned uPercentage = 0; RTFOFF off = 0; RTFOFF cbPercent = cbFile1 / 100; RTFOFF offNextPercent = cbPercent; while (off < (RTFOFF)cbFile1) { /* read the blocks */ RTFOFF cbLeft = cbFile1 - off; size_t cbBlock = cbLeft >= (RTFOFF)cbBuf ? cbBuf : (size_t)cbLeft; rc = RTFileRead(hFile1, pbBuf1, cbBlock, NULL); if (RT_FAILURE(rc)) break; rc = RTFileRead(hFile2, pbBuf2, cbBlock, NULL); if (RT_FAILURE(rc)) break; /* compare */ if (memcmp(pbBuf1, pbBuf2, cbBlock)) { rc = VERR_NOT_EQUAL; break; } /* advance */ off += cbBlock; if (pfnProgress && offNextPercent < off) { while (offNextPercent < off) { uPercentage++; offNextPercent += cbPercent; } rc = pfnProgress(uPercentage, pvUser); if (RT_FAILURE(rc)) break; } } #if 0 /* * Compare OS specific data (EAs and stuff). */ if (RT_SUCCESS(rc)) rc = rtFileCompareOSStuff(hFile1, hFile2); #endif /* 100% */ if (pfnProgress && uPercentage < 100 && RT_SUCCESS(rc)) rc = pfnProgress(100, pvUser); } } } else rc = VERR_NO_MEMORY; RTMemTmpFree(pbBuf2Free); RTMemTmpFree(pbBuf1Free); return rc; }
RTDECL(int) RTFileCopyByHandlesEx(RTFILE FileSrc, RTFILE FileDst, PFNRTPROGRESS pfnProgress, void *pvUser) { /* * Validate input. */ AssertMsgReturn(RTFileIsValid(FileSrc), ("FileSrc=%RTfile\n", FileSrc), VERR_INVALID_PARAMETER); AssertMsgReturn(RTFileIsValid(FileDst), ("FileDst=%RTfile\n", FileDst), VERR_INVALID_PARAMETER); AssertMsgReturn(!pfnProgress || VALID_PTR(pfnProgress), ("pfnProgress=%p\n", pfnProgress), VERR_INVALID_PARAMETER); /* * Save file offset. */ RTFOFF offSrcSaved; int rc = RTFileSeek(FileSrc, 0, RTFILE_SEEK_CURRENT, (uint64_t *)&offSrcSaved); if (RT_FAILURE(rc)) return rc; /* * Get the file size. */ RTFOFF cbSrc; rc = RTFileSeek(FileSrc, 0, RTFILE_SEEK_END, (uint64_t *)&cbSrc); if (RT_FAILURE(rc)) return rc; /* * Allocate buffer. */ size_t cbBuf; uint8_t *pbBufFree = NULL; uint8_t *pbBuf; if (cbSrc < _512K) { cbBuf = 8*_1K; pbBuf = (uint8_t *)alloca(cbBuf); } else { cbBuf = _128K; pbBuf = pbBufFree = (uint8_t *)RTMemTmpAlloc(cbBuf); } if (pbBuf) { /* * Seek to the start of each file * and set the size of the destination file. */ rc = RTFileSeek(FileSrc, 0, RTFILE_SEEK_BEGIN, NULL); if (RT_SUCCESS(rc)) { rc = RTFileSeek(FileDst, 0, RTFILE_SEEK_BEGIN, NULL); if (RT_SUCCESS(rc)) rc = RTFileSetSize(FileDst, cbSrc); if (RT_SUCCESS(rc) && pfnProgress) rc = pfnProgress(0, pvUser); if (RT_SUCCESS(rc)) { /* * Copy loop. */ unsigned uPercentage = 0; RTFOFF off = 0; RTFOFF cbPercent = cbSrc / 100; RTFOFF offNextPercent = cbPercent; while (off < cbSrc) { /* copy block */ RTFOFF cbLeft = cbSrc - off; size_t cbBlock = cbLeft >= (RTFOFF)cbBuf ? cbBuf : (size_t)cbLeft; rc = RTFileRead(FileSrc, pbBuf, cbBlock, NULL); if (RT_FAILURE(rc)) break; rc = RTFileWrite(FileDst, pbBuf, cbBlock, NULL); if (RT_FAILURE(rc)) break; /* advance */ off += cbBlock; if (pfnProgress && offNextPercent < off) { while (offNextPercent < off) { uPercentage++; offNextPercent += cbPercent; } rc = pfnProgress(uPercentage, pvUser); if (RT_FAILURE(rc)) break; } } #if 0 /* * Copy OS specific data (EAs and stuff). */ rtFileCopyOSStuff(FileSrc, FileDst); #endif /* 100% */ if (pfnProgress && uPercentage < 100 && RT_SUCCESS(rc)) rc = pfnProgress(100, pvUser); } } RTMemTmpFree(pbBufFree); } else rc = VERR_NO_MEMORY; /* * Restore source position. */ RTFileSeek(FileSrc, offSrcSaved, RTFILE_SEEK_BEGIN, NULL); return rc; }