Changeset 21892 in vbox for trunk/src/VBox/VMM
- Timestamp:
- Jul 30, 2009 2:39:41 PM (16 years ago)
- svn:sync-xref-src-repo-rev:
- 50541
- Location:
- trunk/src/VBox/VMM
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/VMM/SSM-new.cpp
r21871 r21892 2069 2069 2070 2070 /** 2071 * Used by SSMR3Seek to position the stream at the new unit. 2071 2072 * 2072 2073 * @returns VBox stutus code. … … 2074 2075 * @param off The seek offset. 2075 2076 * @param uMethod The seek method. 2076 * @param poff Where to optionally store the new file offset.2077 */ 2078 static int ssmR3StrmSeek(PSSMSTRM pStrm, int64_t off, uint32_t uMethod, uint 64_t *poff)2077 * @param u32CurCRC The current CRC at the seek position. 2078 */ 2079 static int ssmR3StrmSeek(PSSMSTRM pStrm, int64_t off, uint32_t uMethod, uint32_t u32CurCRC) 2079 2080 { 2080 2081 AssertReturn(!pStrm->fWrite, VERR_NOT_SUPPORTED); … … 2085 2086 if (RT_SUCCESS(rc)) 2086 2087 { 2088 pStrm->fNeedSeek = false; 2087 2089 pStrm->offCurStream = offStream; 2088 pStrm->off = 0;2090 pStrm->off = 0; 2089 2091 pStrm->offStreamCRC = 0; 2090 pStrm->u32StreamCRC = 0; 2092 if (pStrm->fChecksummed) 2093 pStrm->u32StreamCRC = u32CurCRC; 2091 2094 if (pStrm->pCur) 2092 2095 { … … 2094 2097 pStrm->pCur = NULL; 2095 2098 } 2096 if (poff)2097 *poff = offStream;2098 2099 } 2099 2100 return rc; … … 2185 2186 2186 2187 return rc; 2187 }2188 2189 2190 2191 /**2192 * Calculate the checksum of a file portion.2193 *2194 * @returns VBox status.2195 * @param pStrm The stream handle2196 * @param off Where to start checksumming.2197 * @param cb How much to checksum.2198 * @param pu32CRC Where to store the calculated checksum.2199 */2200 static int ssmR3CalcChecksum(PSSMSTRM pStrm, uint64_t off, uint64_t cb, uint32_t *pu32CRC)2201 {2202 /*2203 * Allocate a buffer.2204 */2205 const size_t cbBuf = _32K;2206 void *pvBuf = RTMemTmpAlloc(cbBuf);2207 if (!pvBuf)2208 return VERR_NO_TMP_MEMORY;2209 2210 /*2211 * Loop reading and calculating CRC32.2212 */2213 int rc = VINF_SUCCESS;2214 uint32_t u32CRC = RTCrc32Start();2215 while (cb > 0)2216 {2217 /* read chunk */2218 size_t cbToRead = cbBuf;2219 if (cb < cbBuf)2220 cbToRead = cb;2221 rc = ssmR3StrmPeekAt(pStrm, off, pvBuf, cbToRead, NULL);2222 if (RT_FAILURE(rc))2223 {2224 AssertMsgFailed(("Failed with rc=%Rrc while calculating crc.\n", rc));2225 RTMemTmpFree(pvBuf);2226 return rc;2227 }2228 2229 /* update total */2230 cb -= cbToRead;2231 2232 /* calc crc32. */2233 u32CRC = RTCrc32Process(u32CRC, pvBuf, cbToRead);2234 }2235 RTMemTmpFree(pvBuf);2236 2237 /* store the calculated crc */2238 u32CRC = RTCrc32Finish(u32CRC);2239 Log(("SSM: u32CRC=0x%08x\n", u32CRC));2240 *pu32CRC = u32CRC;2241 2242 return VINF_SUCCESS;2243 2188 } 2244 2189 … … 2676 2621 2677 2622 /** 2623 * Calculate the checksum of a file portion. 2624 * 2625 * @returns VBox status. 2626 * @param pStrm The stream handle 2627 * @param off Where to start checksumming. 2628 * @param cb How much to checksum. 2629 * @param pu32CRC Where to store the calculated checksum. 2630 */ 2631 static int ssmR3CalcChecksum(PSSMSTRM pStrm, uint64_t off, uint64_t cb, uint32_t *pu32CRC) 2632 { 2633 /* 2634 * Allocate a buffer. 2635 */ 2636 const size_t cbBuf = _32K; 2637 void *pvBuf = RTMemTmpAlloc(cbBuf); 2638 if (!pvBuf) 2639 return VERR_NO_TMP_MEMORY; 2640 2641 /* 2642 * Loop reading and calculating CRC32. 2643 */ 2644 int rc = VINF_SUCCESS; 2645 uint32_t u32CRC = RTCrc32Start(); 2646 while (cb > 0) 2647 { 2648 /* read chunk */ 2649 size_t cbToRead = cbBuf; 2650 if (cb < cbBuf) 2651 cbToRead = cb; 2652 rc = ssmR3StrmPeekAt(pStrm, off, pvBuf, cbToRead, NULL); 2653 if (RT_FAILURE(rc)) 2654 { 2655 AssertMsgFailed(("Failed with rc=%Rrc while calculating crc.\n", rc)); 2656 RTMemTmpFree(pvBuf); 2657 return rc; 2658 } 2659 2660 /* advance */ 2661 cb -= cbToRead; 2662 off += cbToRead; 2663 2664 /* calc crc32. */ 2665 u32CRC = RTCrc32Process(u32CRC, pvBuf, cbToRead); 2666 } 2667 RTMemTmpFree(pvBuf); 2668 2669 /* store the calculated crc */ 2670 u32CRC = RTCrc32Finish(u32CRC); 2671 Log(("SSM: u32CRC=0x%08x\n", u32CRC)); 2672 *pu32CRC = u32CRC; 2673 2674 return VINF_SUCCESS; 2675 } 2676 2677 2678 /** 2678 2679 * Validates the header information stored in the handle. 2679 2680 * … … 2741 2742 2742 2743 /** 2743 * Validates the integrity of a saved state file, it also initializes2744 * u32StreamCRC for v2.0+.2744 * Reads the header, detects the format version and performs integrity 2745 * validations. 2745 2746 * 2746 2747 * @returns VBox status. 2747 2748 * @param File File to validate. 2748 2749 * The file position is undefined on return. 2749 * @param fChecksumIt Whether to checksum the file or not. 2750 * @param fChecksumIt Whether to checksum the file or not. This will 2751 * be ignored if it the stream isn't a file. 2750 2752 * @param fChecksumOnRead Whether to validate the checksum while reading 2751 2753 * the stream instead of up front. If not possible, … … 2753 2755 * @param pHdr Where to store the file header. 2754 2756 */ 2755 static int ssmR3 ValidateFile(PSSMHANDLE pSSM, bool fChecksumIt, bool fChecksumOnRead)2757 static int ssmR3HeaderAndValidate(PSSMHANDLE pSSM, bool fChecksumIt, bool fChecksumOnRead) 2756 2758 { 2757 2759 /* … … 2918 2920 if (u32CRC != pSSM->u.Read.u32LoadCRC) 2919 2921 { 2920 LogRel(("SSM: Invalid CRC! Calculated %#010x, in header %#010x\n", u32CRC, pSSM->u.Read.u32LoadCRC));2922 LogRel(("SSM: Invalid CRC! Calculated %#010x, in footer %#010x\n", u32CRC, pSSM->u.Read.u32LoadCRC)); 2921 2923 return VERR_SSM_INTEGRITY_CRC; 2922 2924 } … … 3086 3088 if (RT_SUCCESS(rc)) 3087 3089 { 3088 rc = ssmR3 ValidateFile(pSSM, fChecksumIt, fChecksumOnRead);3090 rc = ssmR3HeaderAndValidate(pSSM, fChecksumIt, fChecksumOnRead); 3089 3091 if (RT_SUCCESS(rc)) 3090 3092 return rc; … … 3728 3730 * Walk the data units until we find EOF or a match. 3729 3731 */ 3730 size_t cbUnit = strlen(pszUnit) + 1;3731 AssertLogRelReturn(cbUnit <= SSM_MAX_NAME_SIZE, VERR_SSM_UNIT_NOT_FOUND);3732 size_t cbUnitNm = strlen(pszUnit) + 1; 3733 AssertLogRelReturn(cbUnitNm <= SSM_MAX_NAME_SIZE, VERR_SSM_UNIT_NOT_FOUND); 3732 3734 char szName[SSM_MAX_NAME_SIZE]; 3733 3735 SSMFILEUNITHDRV1 UnitHdr; … … 3737 3739 * Read the unit header and verify it. 3738 3740 */ 3739 /** @todo this doesn't work when we get an I/O thread... */ 3740 int rc = RTFileReadAt(pSSM->Strm.hFile, off, &UnitHdr, RT_OFFSETOF(SSMFILEUNITHDR, szName), NULL); 3741 int rc = ssmR3StrmPeekAt(&pSSM->Strm, off, &UnitHdr, RT_OFFSETOF(SSMFILEUNITHDR, szName), NULL); 3741 3742 AssertRCReturn(rc, rc); 3742 3743 if (!memcmp(&UnitHdr.achMagic[0], SSMFILEUNITHDR_MAGIC, sizeof(SSMFILEUNITHDR_MAGIC))) … … 3746 3747 */ 3747 3748 if ( UnitHdr.u32Instance == iInstance 3748 && UnitHdr.cchName == cbUnit )3749 && UnitHdr.cchName == cbUnitNm) 3749 3750 { 3750 rc = RTFileRead(pSSM->Strm.hFile, szName, cbUnit, NULL);3751 rc = ssmR3StrmPeekAt(&pSSM->Strm, off + RT_OFFSETOF(SSMFILEUNITHDR, szName), szName, cbUnitNm, NULL); 3751 3752 AssertRCReturn(rc, rc); 3752 3753 AssertLogRelMsgReturn(!szName[UnitHdr.cchName - 1], 3753 (" Unit name '%.*s' was not properly terminated.\n", cbUnit , szName),3754 (" Unit name '%.*s' was not properly terminated.\n", cbUnitNm, szName), 3754 3755 VERR_SSM_INTEGRITY); 3755 3756 … … 3757 3758 * Does the name match? 3758 3759 */ 3759 if (!memcmp(szName, pszUnit, cbUnit ))3760 if (!memcmp(szName, pszUnit, cbUnitNm)) 3760 3761 { 3761 pSSM->cbUnitLeftV1 = UnitHdr.cbUnit - RT_OFFSETOF(SSMFILEUNITHDR, szName[cbUnit]); 3762 rc = ssmR3StrmSeek(&pSSM->Strm, off + RT_OFFSETOF(SSMFILEUNITHDR, szName) + cbUnitNm, RTFILE_SEEK_BEGIN, 0); 3763 pSSM->cbUnitLeftV1 = UnitHdr.cbUnit - RT_OFFSETOF(SSMFILEUNITHDR, szName[cbUnitNm]); 3762 3764 pSSM->offUnit = 0; 3763 3765 if (piVersion) … … 3794 3796 */ 3795 3797 uint64_t const offDir = pSSM->u.Read.cbLoadFile - sizeof(SSMFILEFTR) - cbDir; 3796 /** @todo this doesn't work when we get an I/O thread... */ 3797 int rc = RTFileReadAt(pSSM->Strm.hFile, offDir, pDir, cbDir, NULL); 3798 int rc = ssmR3StrmPeekAt(&pSSM->Strm, offDir, pDir, cbDir, NULL); 3798 3799 AssertLogRelRCReturn(rc, rc); 3799 3800 AssertLogRelReturn(!memcmp(pDir->szMagic, SSMFILEDIR_MAGIC, sizeof(pDir->szMagic)), VERR_SSM_INTEGRITY); … … 3810 3811 * Search the directory. 3811 3812 */ 3812 size_t cbUnit 3813 uint32_t const u32NameCRC = RTCrc32(pszUnit, cbUnit - 1);3813 size_t cbUnitNm = strlen(pszUnit) + 1; 3814 uint32_t const u32NameCRC = RTCrc32(pszUnit, cbUnitNm - 1); 3814 3815 for (uint32_t i = 0; i < cDirEntries; i++) 3815 3816 { … … 3827 3828 RT_ZERO(UnitHdr); 3828 3829 } 3829 /** @todo this doesn't work when we get an I/O thread... */ 3830 rc = RTFileReadAt(pSSM->Strm.hFile, pDir->aEntries[i].off, &UnitHdr, cbToRead, NULL); 3830 rc = ssmR3StrmPeekAt(&pSSM->Strm, pDir->aEntries[i].off, &UnitHdr, cbToRead, NULL); 3831 3831 AssertLogRelRCReturn(rc, rc); 3832 3832 … … 3854 3854 * Ok, it is valid, get on with the comparing now. 3855 3855 */ 3856 if ( UnitHdr.cbName == cbUnit 3857 && !memcmp(UnitHdr.szName, pszUnit, cbUnit ))3856 if ( UnitHdr.cbName == cbUnitNm 3857 && !memcmp(UnitHdr.szName, pszUnit, cbUnitNm)) 3858 3858 { 3859 3859 if (piVersion) 3860 3860 *piVersion = UnitHdr.u32Version; 3861 /** @todo this doesn't work when we get an I/O thread... */ 3862 rc = RTFileSeek(pSSM->Strm.hFile, pDir->aEntries[i].off + cbUnitHdr, RTFILE_SEEK_BEGIN, NULL);3861 rc = ssmR3StrmSeek(&pSSM->Strm, pDir->aEntries[i].off + cbUnitHdr, RTFILE_SEEK_BEGIN, 3862 RTCrc32Process(UnitHdr.u32CurStreamCRC, &UnitHdr, cbUnitHdr)); 3863 3863 AssertLogRelRCReturn(rc, rc); 3864 3865 if (pSSM->Strm.fChecksummed)3866 pSSM->Strm.u32StreamCRC = RTCrc32Process(UnitHdr.u32CurStreamCRC, &UnitHdr, cbUnitHdr);3867 3868 3864 ssmR3DataReadBeginV2(pSSM); 3869 3865 return VINF_SUCCESS; -
trunk/src/VBox/VMM/testcase/tstSSM.cpp
r21793 r21892 48 48 * Defined Constants And Macros * 49 49 *******************************************************************************/ 50 #define TSTSSM_BIG_CONFIG 150 //#define TSTSSM_BIG_CONFIG 1 51 51 52 52 #ifdef TSTSSM_BIG_CONFIG
Note:
See TracChangeset
for help on using the changeset viewer.