VirtualBox

Changeset 15503 in vbox for trunk


Ignore:
Timestamp:
Dec 15, 2008 1:26:31 PM (16 years ago)
Author:
vboxsync
Message:

SSM, CPUM: Moved the GCPtr/GCPhys sizes into the file header instead of out sourcing it to CPUM, bumped header version (warning: not forward compatible). Assumes 32-bit RTGCPTR on 32-bit hosts using the old header, this will conflict with saved states from the last few days because of 64-bit guest on 32-bit hosts changes but there is no way around that. (64-bit hosts are not affected by this latter issue as they've been using 64-bit guest pointers since 2.0.)

Location:
trunk
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/include/VBox/err.h

    r15366 r15503  
    449449 */
    450450/** The specified data unit already exist. */
    451 #define VERR_SSM_UNIT_EXISTS                (-1800)
     451#define VERR_SSM_UNIT_EXISTS                    (-1800)
    452452/** The specified data unit wasn't found. */
    453 #define VERR_SSM_UNIT_NOT_FOUND             (-1801)
     453#define VERR_SSM_UNIT_NOT_FOUND                 (-1801)
    454454/** The specified data unit wasn't owned by caller. */
    455 #define VERR_SSM_UNIT_NOT_OWNER             (-1802)
     455#define VERR_SSM_UNIT_NOT_OWNER                 (-1802)
    456456/** General saved state file integrity error. */
    457 #define VERR_SSM_INTEGRITY                  (-1810)
     457#define VERR_SSM_INTEGRITY                      (-1810)
    458458/** The saved state file magic was not recognized. */
    459 #define VERR_SSM_INTEGRITY_MAGIC            (-1811)
     459#define VERR_SSM_INTEGRITY_MAGIC                (-1811)
    460460/** The saved state file version is not supported. */
    461 #define VERR_SSM_INTEGRITY_VERSION          (-1812)
     461#define VERR_SSM_INTEGRITY_VERSION              (-1812)
    462462/** The saved state file size didn't match the one in the header. */
    463 #define VERR_SSM_INTEGRITY_SIZE             (-1813)
     463#define VERR_SSM_INTEGRITY_SIZE                 (-1813)
    464464/** The CRC of the saved state file did match. */
    465 #define VERR_SSM_INTEGRITY_CRC              (-1814)
     465#define VERR_SSM_INTEGRITY_CRC                  (-1814)
    466466/** The current virtual machine id didn't match the virtual machine id. */
    467 #define VERR_SMM_INTEGRITY_MACHINE          (-1815)
     467#define VERR_SMM_INTEGRITY_MACHINE              (-1815)
    468468/** Invalid unit magic (internal data tag). */
    469 #define VERR_SSM_INTEGRITY_UNIT_MAGIC       (-1816)
     469#define VERR_SSM_INTEGRITY_UNIT_MAGIC           (-1816)
    470470/** The file contained a data unit which no-one wants. */
    471 #define VERR_SSM_INTEGRITY_UNIT_NOT_FOUND   (-1817)
     471#define VERR_SSM_INTEGRITY_UNIT_NOT_FOUND       (-1817)
     472/** Incorrect type sizes in the header. */
     473#define VERR_SSM_INTEGRITY_SIZES                (-1818)
     474/** Incorrect version numbers in the header. */
     475#define VERR_SSM_INTEGRITY_VBOX_VERSION         (-1819)
    472476/** A data unit in the saved state file was defined but didn't any
    473477 * routine for processing it. */
    474 #define VERR_SSM_NO_LOAD_EXEC               (-1818)
     478#define VERR_SSM_NO_LOAD_EXEC                   (-1820)
    475479/** A restore routine attempted to load more data then the unit contained. */
    476 #define VERR_SSM_LOADED_TOO_MUCH            (-1819)
     480#define VERR_SSM_LOADED_TOO_MUCH                (-1821)
    477481/** Not in the correct state for the attempted operation. */
    478 #define VERR_SSM_INVALID_STATE              (-1820)
     482#define VERR_SSM_INVALID_STATE                  (-1822)
    479483
    480484/** Unsupported data unit version.
    481485 * A SSM user returns this if it doesn't know the u32Version. */
    482 #define VERR_SSM_UNSUPPORTED_DATA_UNIT_VERSION  (-1821)
     486#define VERR_SSM_UNSUPPORTED_DATA_UNIT_VERSION  (-1823)
    483487/** The format of a data unit has changed.
    484488 * A SSM user returns this if it's not able to read the format for
    485489 * other reasons than u32Version. */
    486 #define VERR_SSM_DATA_UNIT_FORMAT_CHANGED       (-1822)
     490#define VERR_SSM_DATA_UNIT_FORMAT_CHANGED       (-1824)
    487491/** The CPUID instruction returns different information when loading than when saved.
    488492 * Normally caused by hardware changes on the host, but could also be caused by
    489493 * changes in the BIOS setup. */
    490 #define VERR_SSM_LOAD_CPUID_MISMATCH            (-1823)
     494#define VERR_SSM_LOAD_CPUID_MISMATCH            (-1825)
    491495/** The RAM size differes between the saved state and the VM config. */
    492 #define VERR_SSM_LOAD_MEMORY_SIZE_MISMATCH      (-1824)
     496#define VERR_SSM_LOAD_MEMORY_SIZE_MISMATCH      (-1826)
    493497/** The state doesn't match the VM configuration in one or another way.
    494498 * (There are certain PCI reconfiguration which the OS could potentially
    495499 * do which can cause this problem. Check this out when it happens.) */
    496 #define VERR_SSM_LOAD_CONFIG_MISMATCH           (-1825)
     500#define VERR_SSM_LOAD_CONFIG_MISMATCH           (-1827)
    497501/** The virtual clock freqency differs too much.
    498502 * The clock source for the virtual time isn't reliable or the code have changed. */
    499 #define VERR_SSM_VIRTUAL_CLOCK_HZ               (-1826)
     503#define VERR_SSM_VIRTUAL_CLOCK_HZ               (-1828)
    500504/** A timeout occured while waiting for async IDE operations to finish. */
    501 #define VERR_SSM_IDE_ASYNC_TIMEOUT              (-1827)
     505#define VERR_SSM_IDE_ASYNC_TIMEOUT              (-1829)
    502506/** One of the structure magics was wrong. */
    503 #define VERR_SSM_STRUCTURE_MAGIC                (-1828)
     507#define VERR_SSM_STRUCTURE_MAGIC                (-1830)
    504508/** The data in the saved state doesn't confirm to expectations. */
    505 #define VERR_SSM_UNEXPECTED_DATA                (-1829)
     509#define VERR_SSM_UNEXPECTED_DATA                (-1831)
     510/** Trying to read a 64-bit guest physical address into a 32-bit variable. */
     511#define VERR_SSM_GCPHYS_OVERFLOW                (-1832)
     512/** Trying to read a 64-bit guest virtual address into a 32-bit variable. */
     513#define VERR_SSM_GCPTR_OVERFLOW                 (-1833)
    506514/** @} */
    507515
  • trunk/src/VBox/VMM/CPUM.cpp

    r15414 r15503  
    773773static DECLCALLBACK(int) cpumR3Save(PVM pVM, PSSMHANDLE pSSM)
    774774{
    775     /* Set the size of RTGCPTR for use of SSMR3Get/PutGCPtr. */
    776     SSMR3SetGCPtrSize(pSSM, sizeof(RTGCPTR));
    777 
    778775    /*
    779776     * Save.
     
    929926    if (u32Version == CPUM_SAVED_STATE_VERSION_VER1_6)
    930927        SSMR3SetGCPtrSize(pSSM, sizeof(RTGCPTR32));
    931     else
    932         SSMR3SetGCPtrSize(pSSM, sizeof(RTGCPTR));
     928    else if (u32Version <= CPUM_SAVED_STATE_VERSION)
     929        SSMR3SetGCPtrSize(pSSM, HC_ARCH_BITS == 32 ? sizeof(RTGCPTR32) : sizeof(RTGCPTR));
    933930
    934931    /*
  • trunk/src/VBox/VMM/SSM.cpp

    r14075 r15503  
    8484/** Saved state file v1.1 magic. */
    8585#define SSMFILEHDR_MAGIC_V1_1   "\177VirtualBox SavedState V1.1\n"
     86/** Saved state file v1.2 magic. */
     87#define SSMFILEHDR_MAGIC_V1_2   "\177VirtualBox SavedState V1.2\n\0\0\0"
    8688
    8789/** Data unit magic. */
     
    102104typedef enum SSMSTATE
    103105{
    104     SSMSTATE_SAVE_PREP = 1,
     106    SSMSTATE_INVALID = 0,
     107    SSMSTATE_SAVE_PREP,
    105108    SSMSTATE_SAVE_EXEC,
    106109    SSMSTATE_SAVE_DONE,
     
    158161    unsigned        uPercentDone;
    159162
    160     /** RTGCPTR size in bytes */
     163    /** RTGCPHYS size in bytes. (Only applicable when loading/reading.) */
     164    unsigned        cbGCPhys;
     165    /** RTGCPTR size in bytes. (Only applicable when loading/reading.) */
    161166    unsigned        cbGCPtr;
     167    /** Whether cbGCPtr is fixed or settable. */
     168    bool            fFixedGCPtrSize;
    162169} SSMHANDLE;
    163170
     
    165172/**
    166173 * Header of the saved state file.
     174 *
     175 * @remarks This is a superset of SSMFILEHDRV11.
    167176 */
    168177typedef struct SSMFILEHDR
     178{
     179    /** Magic string which identifies this file as a version of VBox saved state
     180     *  file format (SSMFILEHDR_MAGIC_V1_2). */
     181    char            achMagic[32];
     182    /** The size of this file. Used to check
     183     * whether the save completed and that things are fine otherwise. */
     184    uint64_t        cbFile;
     185    /** File checksum. The actual calculation skips past the u32CRC field. */
     186    uint32_t        u32CRC;
     187    /** Padding. */
     188    uint32_t        u32Reserved;
     189    /** The machine UUID. (Ignored if NIL.) */
     190    RTUUID          MachineUuid;
     191
     192    /** The major version number. */
     193    uint16_t        u16VerMajor;
     194    /** The minor version number. */
     195    uint16_t        u16VerMinor;
     196    /** The build number. */
     197    uint32_t        u32VerBuild;
     198    /** The SVN revision. */
     199    uint32_t        u32SvnRev;
     200
     201    /** 32 or 64 depending on the host. */
     202    uint8_t         cHostBits;
     203    /** The size of RTGCPHYS. */
     204    uint8_t         cbGCPhys;
     205    /** The size of RTGCPTR. */
     206    uint8_t         cbGCPtr;
     207    /** Padding. */
     208    uint8_t         au8Reserved;
     209} SSMFILEHDR;
     210AssertCompileSize(SSMFILEHDR, 64+16);
     211AssertCompileMemberSize(SSMFILEHDR, achMagic, sizeof(SSMFILEHDR_MAGIC_V1_2));
     212/** Pointer to a saved state file header. */
     213typedef SSMFILEHDR *PSSMFILEHDR;
     214
     215
     216/**
     217 * Header of the saved state file, version 1.1.
     218 */
     219typedef struct SSMFILEHDRV11
    169220{
    170221    /** Magic string which identifies this file as a version of VBox saved state
     
    180231    /** The machine UUID. (Ignored if NIL.) */
    181232    RTUUID          MachineUuid;
    182 } SSMFILEHDR;
    183 AssertCompileSize(SSMFILEHDR, 64);
     233} SSMFILEHDRV11;
     234AssertCompileSize(SSMFILEHDRV11, 64);
    184235/** Pointer to a saved state file header. */
    185 typedef SSMFILEHDR *PSSMFILEHDR;
     236typedef SSMFILEHDRV11 *PSSMFILEHDRV11;
    186237
    187238
     
    278329
    279330/**
    280  * For saving the version + revision and stuff.
     331 * For saving usful things without having to go thru the tedious process of
     332 * adding it to the header.
    281333 *
    282334 * @returns VBox status code.
     
    292344     * Terminated by two empty strings.
    293345     */
    294     SSMR3PutStrZ(pSSM, "VBox Version");
    295     SSMR3PutStrZ(pSSM, VBOX_VERSION_STRING);
    296     SSMR3PutStrZ(pSSM, "VBox Revision");
    297     RTStrPrintf(szTmp, sizeof(szTmp), "%d", VMMGetSvnRev());
    298     SSMR3PutStrZ(pSSM, szTmp);
    299346#ifdef VBOX_OSE
    300347    SSMR3PutStrZ(pSSM, "OSE");
     
    324371     * Terminated by two empty strings.
    325372     */
    326     LogRel(("SSM: Saved state info:\n"));
    327     for (;;)
     373    for (unsigned i = 0; ; i++)
    328374    {
    329375        char szVar[128];
     
    335381        if (!szVar[0] && !szValue[0])
    336382            break;
     383        if (i == 0)
     384            LogRel(("SSM: Saved state info:\n"));
    337385        LogRel(("SSM:   %s: %s\n", szVar, szValue));
    338386    }
     
    925973     */
    926974    SSMHANDLE Handle       = {0};
    927     Handle.enmAfter        = enmAfter;
    928     Handle.pVM             = pVM;
    929     Handle.cbFileHdr       = sizeof(SSMFILEHDR);
    930     Handle.pfnProgress     = pfnProgress;
    931     Handle.pvUser          = pvUser;
    932     Handle.uPercentPrepare = 2;
    933     Handle.uPercentDone    = 20;
     975    Handle.File             = NIL_RTFILE;
     976    Handle.pVM              = pVM;
     977    Handle.cbFileHdr        = sizeof(SSMFILEHDR);
     978    Handle.enmOp            = SSMSTATE_INVALID;
     979    Handle.enmAfter         = enmAfter;
     980    Handle.rc               = VINF_SUCCESS;
     981    Handle.pZipComp         = NULL;
     982    Handle.pZipDecomp       = NULL;
     983    Handle.pfnProgress      = pfnProgress;
     984    Handle.pvUser           = pvUser;
     985    Handle.uPercent         = 0;
     986    Handle.offEstProgress   = 0;
     987    Handle.cbEstTotal       = 0;
     988    Handle.offEst           = 0;
     989    Handle.offEstUnitEnd    = 0;
     990    Handle.uPercentPrepare  = 20;
     991    Handle.uPercentDone     = 2;
     992    Handle.cbGCPhys         = sizeof(RTGCPHYS);
     993    Handle.cbGCPtr          = sizeof(RTGCPTR);
     994    Handle.fFixedGCPtrSize  = true;
    934995
    935996    int rc = RTFileOpen(&Handle.File, pszFilename, RTFILE_O_READWRITE | RTFILE_O_CREATE_REPLACE | RTFILE_O_DENY_WRITE);
     
    9451006     * Write header.
    9461007     */
    947     SSMFILEHDR Hdr = { SSMFILEHDR_MAGIC_V1_1, 0, 0, 0 };
     1008    SSMFILEHDR Hdr =
     1009    {
     1010        /* .achMagic[32] = */ SSMFILEHDR_MAGIC_V1_2,
     1011        /* .cbFile       = */ 0,
     1012        /* .u32CRC       = */ 0,
     1013        /* .u32Reserved  = */ 0,
     1014        /* .MachineUuid  = */ {{0,0,0,0, 0,0,0,0, 0,0,0,0, 0,0,0,0}},
     1015        /* .u16VerMajor  = */ VBOX_VERSION_MAJOR,
     1016        /* .u16VerMinor  = */ VBOX_VERSION_MINOR,
     1017        /* .u32VerBuild  = */ VBOX_VERSION_BUILD,
     1018        /* .u32SvnRev    = */ VMMGetSvnRev(),
     1019        /* .cHostBits    = */ HC_ARCH_BITS,
     1020        /* .cbGCPhys     = */ sizeof(RTGCPHYS),
     1021        /* .cbGCPtr      = */ sizeof(RTGCPTR),
     1022        /* .au8Reserved  = */ 0
     1023    };
    9481024    rc = RTFileWrite(Handle.File, &Hdr, sizeof(Hdr), NULL);
    9491025    if (RT_SUCCESS(rc))
     
    12761352            pHdr->u32Reserved = 0;
    12771353            pHdr->MachineUuid = OldHdr.MachineUuid;
     1354            pHdr->cHostBits   = 32;
    12781355
    12791356            offCrc32 = RT_OFFSETOF(SSMFILEHDRV10X86, u32CRC) + sizeof(pHdr->u32CRC);
     
    12821359        else
    12831360        {
    1284             /* (It's identical to the current, but this doesn't harm us and will
    1285                continue working after future changes.) */
    12861361            SSMFILEHDRV10AMD64 OldHdr;
    12871362            memcpy(&OldHdr, pHdr, sizeof(OldHdr));
     
    12901365            pHdr->u32Reserved = 0;
    12911366            pHdr->MachineUuid = OldHdr.MachineUuid;
     1367            pHdr->cHostBits   = 64;
    12921368
    12931369            offCrc32 = RT_OFFSETOF(SSMFILEHDRV10AMD64, u32CRC) + sizeof(pHdr->u32CRC);
    12941370            *pcbFileHdr = sizeof(OldHdr);
    12951371        }
    1296     }
    1297     else if (memcmp(pHdr->achMagic, SSMFILEHDR_MAGIC_V1_1, sizeof(SSMFILEHDR_MAGIC_V1_1)))
     1372        pHdr->u16VerMajor = 0;
     1373        pHdr->u16VerMinor = 0;
     1374        pHdr->u32VerBuild = 0;
     1375        pHdr->u32SvnRev   = 0;
     1376        pHdr->cbGCPhys    = sizeof(uint32_t);
     1377        pHdr->cbGCPtr     = sizeof(uint32_t);
     1378        pHdr->au8Reserved = 0;
     1379    }
     1380    else if (!memcmp(pHdr->achMagic, SSMFILEHDR_MAGIC_V1_1, sizeof(SSMFILEHDR_MAGIC_V1_1)))
     1381    {
     1382        *pcbFileHdr = sizeof(SSMFILEHDRV11);
     1383        pHdr->u16VerMajor = 0;
     1384        pHdr->u16VerMinor = 0;
     1385        pHdr->u32VerBuild = 0;
     1386        pHdr->u32SvnRev   = 0;
     1387        pHdr->cHostBits   = 0; /* unknown */
     1388        pHdr->cbGCPhys    = sizeof(RTGCPHYS);
     1389        pHdr->cbGCPtr     = 0; /* settable. */
     1390        pHdr->au8Reserved = 0;
     1391    }
     1392    else if (!memcmp(pHdr->achMagic, SSMFILEHDR_MAGIC_V1_2, sizeof(pHdr->achMagic)))
     1393    {
     1394        if (    pHdr->u16VerMajor == 0
     1395            ||  pHdr->u16VerMajor > 1000
     1396            ||  pHdr->u32SvnRev == 0
     1397            ||  pHdr->u32SvnRev > 10000000 /*100M*/)
     1398        {
     1399            LogRel(("SSM: Incorrect version values: %d.%d.%d.r%d\n",
     1400                    pHdr->u16VerMajor, pHdr->u16VerMinor, pHdr->u32VerBuild, pHdr->u32SvnRev));
     1401            return VERR_SSM_INTEGRITY_VBOX_VERSION;
     1402        }
     1403        if (    pHdr->cHostBits != 32
     1404            &&  pHdr->cHostBits != 64)
     1405        {
     1406            LogRel(("SSM: Incorrect cHostBits value: %d\n", pHdr->cHostBits));
     1407            return VERR_SSM_INTEGRITY_SIZES;
     1408        }
     1409        if (    pHdr->cbGCPhys != sizeof(uint32_t)
     1410            &&  pHdr->cbGCPhys != sizeof(uint64_t))
     1411        {
     1412            LogRel(("SSM: Incorrect cbGCPhys value: %d\n", pHdr->cbGCPhys));
     1413            return VERR_SSM_INTEGRITY_SIZES;
     1414        }
     1415        if (    pHdr->cbGCPtr != sizeof(uint32_t)
     1416            &&  pHdr->cbGCPtr != sizeof(uint64_t))
     1417        {
     1418            LogRel(("SSM: Incorrect cbGCPtr value: %d\n", pHdr->cbGCPtr));
     1419            return VERR_SSM_INTEGRITY_SIZES;
     1420        }
     1421    }
     1422    else
    12981423    {
    12991424        Log(("SSM: Unknown file format version. magic=%.*s\n", sizeof(pHdr->achMagic) - 1, pHdr->achMagic));
     
    14101535     * take a long time.
    14111536     */
    1412     SSMHANDLE Handle       = {0};
    1413     Handle.enmAfter        = enmAfter;
    1414     Handle.pVM             = pVM;
    1415     Handle.cbFileHdr       = sizeof(SSMFILEHDR);
    1416     Handle.pfnProgress     = pfnProgress;
    1417     Handle.pvUser          = pvUser;
    1418     Handle.uPercentPrepare = 20;
    1419     Handle.uPercentDone    = 2;
     1537    SSMHANDLE Handle = {0};
     1538    Handle.File             = NIL_RTFILE;
     1539    Handle.pVM              = pVM;
     1540    Handle.cbFileHdr        = sizeof(SSMFILEHDR);
     1541    Handle.enmOp            = SSMSTATE_INVALID;
     1542    Handle.enmAfter         = enmAfter;
     1543    Handle.rc               = VINF_SUCCESS;
     1544    Handle.pZipComp         = NULL;
     1545    Handle.pZipDecomp       = NULL;
     1546    Handle.pfnProgress      = pfnProgress;
     1547    Handle.pvUser           = pvUser;
     1548    Handle.uPercent         = 0;
     1549    Handle.offEstProgress   = 0;
     1550    Handle.cbEstTotal       = 0;
     1551    Handle.offEst           = 0;
     1552    Handle.offEstUnitEnd    = 0;
     1553    Handle.uPercentPrepare  = 20;
     1554    Handle.uPercentDone     = 2;
     1555    Handle.cbGCPhys         = sizeof(RTGCPHYS);
     1556    Handle.cbGCPtr          = sizeof(RTGCPTR);
     1557    Handle.fFixedGCPtrSize  = false;
    14201558
    14211559    int rc = RTFileOpen(&Handle.File, pszFilename, RTFILE_O_READ | RTFILE_O_OPEN | RTFILE_O_DENY_WRITE);
     
    14331571    if (RT_SUCCESS(rc))
    14341572    {
     1573        if (Hdr.cbGCPhys)
     1574            Handle.cbGCPhys = Hdr.cbGCPhys;
     1575        if (Hdr.cbGCPtr)
     1576        {
     1577            Handle.cbGCPtr = Hdr.cbGCPtr;
     1578            Handle.fFixedGCPtrSize = true;
     1579        }
     1580
     1581        if (Handle.cbFileHdr == sizeof(Hdr))
     1582            LogRel(("SSM: File header: Format %.4s, VirtualBox Version %u.%u.%u r%u, %u-bit host, cbGCPhys=%u, cbGCPtr=%u\n",
     1583                    &Hdr.achMagic[sizeof(SSMFILEHDR_MAGIC_BASE) - 1],
     1584                    Hdr.u16VerMajor, Hdr.u16VerMinor, Hdr.u32VerBuild, Hdr.u32SvnRev,
     1585                    Hdr.cHostBits, Hdr.cbGCPhys, Hdr.cbGCPtr));
     1586        else
     1587            LogRel(("SSM: File header: Format %.4s, %u-bit host, cbGCPhys=%u, cbGCPtr=%u\n" ,
     1588                    &Hdr.achMagic[sizeof(SSMFILEHDR_MAGIC_BASE)-1], Hdr.cHostBits, Hdr.cbGCPhys, Hdr.cbGCPtr));
     1589
     1590
    14351591        /*
    14361592         * Clear the per unit flags.
     
    18512007            pSSM->enmOp           = SSMSTATE_OPEN_READ;
    18522008            pSSM->enmAfter        = SSMAFTER_OPENED;
    1853             pSSM->uPercentPrepare = 20;
    1854             pSSM->uPercentDone    = 2;
    18552009            //pSSM->rc            = VINF_SUCCESS;
    18562010            //pSSM->pZipComp      = NULL;
     
    18642018            //pSSM->offEst        = 0;
    18652019            //pSSM->offEstUnitEnd = 0;
     2020            pSSM->uPercentPrepare = 20;
     2021            pSSM->uPercentDone    = 2;
     2022            pSSM->cbGCPhys        = Hdr.cbGCPhys ? Hdr.cbGCPhys : sizeof(RTGCPHYS);
     2023            pSSM->cbGCPtr         = sizeof(RTGCPTR);
     2024            pSSM->fFixedGCPtrSize = false;
     2025            if (Hdr.cbGCPtr)
     2026            {
     2027                pSSM->cbGCPtr         = Hdr.cbGCPtr;
     2028                pSSM->fFixedGCPtrSize = true;
     2029            }
     2030
    18662031            *ppSSM = pSSM;
    18672032            LogFlow(("SSMR3Open: returns VINF_SUCCESS *ppSSM=%p\n", *ppSSM));
    18682033            return VINF_SUCCESS;
    18692034        }
     2035
    18702036        Log(("SSMR3Open: Validation of '%s' failed, rc=%Rrc.\n",  pszFilename, rc));
    18712037        RTFileClose(pSSM->File);
     
    29403106 * @param   pu              Where to store the integer.
    29413107 *
    2942  * @deprecated Silly type, don't use it.
     3108 * @deprecated Silly type with an incorrect size, don't use it.
    29433109 */
    29443110VMMR3DECL(int) SSMR3GetGCUInt(PSSMHANDLE pSSM, PRTGCUINT pu)
    29453111{
    2946     Assert(pSSM->cbGCPtr == sizeof(RTGCPTR32) || pSSM->cbGCPtr == sizeof(RTGCPTR64));
    2947 
    2948     if (pSSM->enmOp == SSMSTATE_LOAD_EXEC || pSSM->enmOp == SSMSTATE_OPEN_READ)
    2949     {
    2950         if (sizeof(*pu) != pSSM->cbGCPtr)
    2951         {
    2952             uint32_t val;
    2953             Assert(sizeof(*pu) == sizeof(uint64_t) && pSSM->cbGCPtr == sizeof(uint32_t));
    2954             int rc = ssmR3Read(pSSM, &val, pSSM->cbGCPtr);
    2955             *pu = val;
    2956             return rc;
    2957         }
    2958         return ssmR3Read(pSSM, pu, sizeof(*pu));
    2959     }
    2960     AssertMsgFailed(("Invalid state %d\n", pSSM->enmOp));
    2961     return VERR_SSM_INVALID_STATE;
     3112    AssertCompile(sizeof(RTGCPTR) == sizeof(*pu));
     3113    return SSMR3GetGCPtr(pSSM, (PRTGCPTR)pu);
    29623114}
    29633115
     
    29723124VMMR3DECL(int) SSMR3GetGCUIntReg(PSSMHANDLE pSSM, PRTGCUINTREG pu)
    29733125{
    2974     Assert(pSSM->cbGCPtr == sizeof(RTGCPTR32) || pSSM->cbGCPtr == sizeof(RTGCPTR64));
    2975 
    2976     if (pSSM->enmOp == SSMSTATE_LOAD_EXEC || pSSM->enmOp == SSMSTATE_OPEN_READ)
    2977     {
    2978         if (sizeof(*pu) != pSSM->cbGCPtr)
    2979         {
    2980             uint32_t val;
    2981             Assert(sizeof(*pu) == sizeof(uint64_t) && pSSM->cbGCPtr == sizeof(uint32_t));
    2982             int rc = ssmR3Read(pSSM, &val, pSSM->cbGCPtr);
    2983             *pu = val;
    2984             return rc;
    2985         }
    2986         return ssmR3Read(pSSM, pu, sizeof(*pu));
    2987     }
    2988     AssertMsgFailed(("Invalid state %d\n", pSSM->enmOp));
    2989     return VERR_SSM_INVALID_STATE;
     3126    AssertCompile(sizeof(RTGCPTR) == sizeof(*pu));
     3127    return SSMR3GetGCPtr(pSSM, (PRTGCPTR)pu);
    29903128}
    29913129
     
    30333171{
    30343172    if (pSSM->enmOp == SSMSTATE_LOAD_EXEC || pSSM->enmOp == SSMSTATE_OPEN_READ)
    3035         return ssmR3Read(pSSM, pGCPhys, sizeof(*pGCPhys));
     3173    {
     3174        if (sizeof(*pGCPhys) != pSSM->cbGCPhys)
     3175        {
     3176            Assert(sizeof(*pGCPhys) == sizeof(uint64_t) || sizeof(*pGCPhys) == sizeof(uint32_t));
     3177            Assert(pSSM->cbGCPhys   == sizeof(uint64_t) || pSSM->cbGCPhys   == sizeof(uint32_t));
     3178            if (pSSM->cbGCPhys == sizeof(uint64_t))
     3179            {
     3180                /* 64-bit saved, 32-bit load: try truncate it. */
     3181                uint64_t u64;
     3182                int rc = ssmR3Read(pSSM, &u64, pSSM->cbGCPhys);
     3183                if (RT_FAILURE(rc))
     3184                    return rc;
     3185                if (u64 >= _4G)
     3186                    return VERR_SSM_GCPHYS_OVERFLOW;
     3187                *pGCPhys = (RTGCPHYS)u64;
     3188                return rc;
     3189            }
     3190            /* 32-bit saved, 64-bit load: clear the high part. */
     3191            *pGCPhys = 0;
     3192        }
     3193        return ssmR3Read(pSSM, pGCPhys, pSSM->cbGCPhys);
     3194    }
    30363195    AssertMsgFailed(("Invalid state %d\n", pSSM->enmOp));
    30373196    return VERR_SSM_INVALID_STATE;
     
    30423201 * Loads a GC virtual address item from the current data unit.
    30433202 *
    3044  * Only applies to:
     3203 * Only applies to in the 1.1 format:
    30453204 *  - SSMR3GetGCPtr
    30463205 *  - SSMR3GetGCUIntPtr
     
    30533212 * @param   pSSM            SSM operation handle.
    30543213 * @param   cbGCPtr         Size of RTGCPTR
     3214 *
     3215 * @remarks This interface only works with saved state version 1.1, if the
     3216 *          format isn't 1.1 the call will be ignored.
    30553217 */
    30563218VMMR3DECL(int) SSMR3SetGCPtrSize(PSSMHANDLE pSSM, unsigned cbGCPtr)
    30573219{
    30583220    Assert(cbGCPtr == sizeof(RTGCPTR32) || cbGCPtr == sizeof(RTGCPTR64));
    3059     Log(("SSMR3SetGCPtrSize %d bytes\n", cbGCPtr));
    3060     pSSM->cbGCPtr = cbGCPtr;
     3221    if (!pSSM->fFixedGCPtrSize)
     3222    {
     3223        Log(("SSMR3SetGCPtrSize: %d -> %d bytes\n", pSSM->cbGCPtr, cbGCPtr));
     3224        pSSM->cbGCPtr = cbGCPtr;
     3225        pSSM->fFixedGCPtrSize = true;
     3226    }
     3227    else if (   pSSM->cbGCPtr != cbGCPtr
     3228             && pSSM->cbFileHdr == sizeof(SSMFILEHDRV11))
     3229        AssertMsgFailed(("SSMR3SetGCPtrSize: already fixed at %d bytes; requested %d bytes\n", pSSM->cbGCPtr, cbGCPtr));
     3230
    30613231    return VINF_SUCCESS;
    30623232}
     
    30723242VMMR3DECL(int) SSMR3GetGCPtr(PSSMHANDLE pSSM, PRTGCPTR pGCPtr)
    30733243{
    3074     Assert(pSSM->cbGCPtr == sizeof(RTGCPTR32) || pSSM->cbGCPtr == sizeof(RTGCPTR64));
    3075 
    30763244    if (pSSM->enmOp == SSMSTATE_LOAD_EXEC || pSSM->enmOp == SSMSTATE_OPEN_READ)
    30773245    {
    30783246        if (sizeof(*pGCPtr) != pSSM->cbGCPtr)
    30793247        {
    3080             RTGCPTR32 val;
    3081             Assert(sizeof(*pGCPtr) == sizeof(uint64_t) && pSSM->cbGCPtr == sizeof(uint32_t));
    3082             int rc = ssmR3Read(pSSM, &val, pSSM->cbGCPtr);
    3083             *pGCPtr = val;
    3084             return rc;
     3248            Assert(sizeof(*pGCPtr) == sizeof(uint64_t) || sizeof(*pGCPtr) == sizeof(uint32_t));
     3249            Assert(pSSM->cbGCPtr   == sizeof(uint64_t) || pSSM->cbGCPtr   == sizeof(uint32_t));
     3250            if (pSSM->cbGCPtr == sizeof(uint64_t))
     3251            {
     3252                /* 64-bit saved, 32-bit load: try truncate it. */
     3253                uint64_t u64;
     3254                int rc = ssmR3Read(pSSM, &u64, pSSM->cbGCPhys);
     3255                if (RT_FAILURE(rc))
     3256                    return rc;
     3257                if (u64 >= _4G)
     3258                    return VERR_SSM_GCPTR_OVERFLOW;
     3259                *pGCPtr = (RTGCPTR)u64;
     3260                return rc;
     3261            }
     3262            /* 32-bit saved, 64-bit load: clear the high part. */
     3263            *pGCPtr = 0;
    30853264        }
    30863265        return ssmR3Read(pSSM, pGCPtr, pSSM->cbGCPtr);
     
    30923271
    30933272/**
     3273 * Loads a GC virtual address (represented as unsigned integer) item from the current data unit.
     3274 *
     3275 * @returns VBox status.
     3276 * @param   pSSM            SSM operation handle.
     3277 * @param   pGCPtr          Where to store the GC virtual address.
     3278 */
     3279VMMR3DECL(int) SSMR3GetGCUIntPtr(PSSMHANDLE pSSM, PRTGCUINTPTR pGCPtr)
     3280{
     3281    AssertCompile(sizeof(RTGCPTR) == sizeof(*pGCPtr));
     3282    return SSMR3GetGCPtr(pSSM, (PRTGCPTR)pGCPtr);
     3283}
     3284
     3285
     3286/**
    30943287 * Loads an RC virtual address item from the current data unit.
    30953288 *
     
    31033296        return ssmR3Read(pSSM, pRCPtr, sizeof(*pRCPtr));
    31043297
    3105     AssertMsgFailed(("Invalid state %d\n", pSSM->enmOp));
    3106     return VERR_SSM_INVALID_STATE;
    3107 }
    3108 
    3109 
    3110 /**
    3111  * Loads a GC virtual address (represented as unsigned integer) item from the current data unit.
    3112  *
    3113  * @returns VBox status.
    3114  * @param   pSSM            SSM operation handle.
    3115  * @param   pGCPtr          Where to store the GC virtual address.
    3116  */
    3117 VMMR3DECL(int) SSMR3GetGCUIntPtr(PSSMHANDLE pSSM, PRTGCUINTPTR pGCPtr)
    3118 {
    3119     Assert(pSSM->cbGCPtr == sizeof(RTGCPTR32) || pSSM->cbGCPtr == sizeof(RTGCPTR64));
    3120 
    3121     if (pSSM->enmOp == SSMSTATE_LOAD_EXEC || pSSM->enmOp == SSMSTATE_OPEN_READ)
    3122     {
    3123         if (sizeof(*pGCPtr) != pSSM->cbGCPtr)
    3124         {
    3125             RTGCUINTPTR32 val;
    3126             Assert(sizeof(*pGCPtr) == sizeof(uint64_t) && pSSM->cbGCPtr == sizeof(uint32_t));
    3127             int rc = ssmR3Read(pSSM, &val, pSSM->cbGCPtr);
    3128             *pGCPtr = val;
    3129             return rc;
    3130         }
    3131         return ssmR3Read(pSSM, pGCPtr, pSSM->cbGCPtr);
    3132     }
    31333298    AssertMsgFailed(("Invalid state %d\n", pSSM->enmOp));
    31343299    return VERR_SSM_INVALID_STATE;
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette