VirtualBox

Changeset 39882 in vbox for trunk/src/VBox/Main/src-client


Ignore:
Timestamp:
Jan 26, 2012 12:54:50 AM (13 years ago)
Author:
vboxsync
Message:

Config.kmk,VMMDev,Main,QtGui,VBoxManage: Refactored IGuest::additionsVersion and associated acts, splitting it up into additionsVersion and additionsRevision like IVirtualBox and IExtPack handles versioning. Fixed missing saved state in VMMDev where the VMMDevReq_ReportGuestInfo2 info was not saved and Main+Frontends led to believe we were running guest additions older than 3.2. The changes have be subjected to limited testing. Added TODOs for another missing save in VMMDev.

Location:
trunk/src/VBox/Main/src-client
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Main/src-client/GuestImpl.cpp

    r39824 r39882  
    3636#include <iprt/cpp/utils.h>
    3737#include <VBox/vmm/pgm.h>
     38#include <VBox/version.h>
    3839
    3940// defines
     
    164165/////////////////////////////////////////////////////////////////////////////
    165166
    166 STDMETHODIMP Guest::COMGETTER(OSTypeId)(BSTR *aOSTypeId)
    167 {
    168     CheckComArgOutPointerValid(aOSTypeId);
    169 
    170     AutoCaller autoCaller(this);
    171     if (FAILED(autoCaller.rc())) return autoCaller.rc();
    172 
    173     AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
    174 
    175     /* Redirect the call to IMachine if no additions are installed. */
    176     if (mData.mAdditionsVersion.isEmpty())
    177         return mParent->machine()->COMGETTER(OSTypeId)(aOSTypeId);
    178 
    179     mData.mOSTypeId.cloneTo(aOSTypeId);
    180 
    181     return S_OK;
    182 }
    183 
    184 STDMETHODIMP Guest::COMGETTER(AdditionsRunLevel) (AdditionsRunLevelType_T *aRunLevel)
    185 {
    186     AutoCaller autoCaller(this);
    187     if (FAILED(autoCaller.rc())) return autoCaller.rc();
    188 
    189     AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
    190 
    191     *aRunLevel = mData.mAdditionsRunLevel;
    192 
    193     return S_OK;
    194 }
    195 
    196 STDMETHODIMP Guest::COMGETTER(AdditionsVersion) (BSTR *aAdditionsVersion)
    197 {
    198     CheckComArgOutPointerValid(aAdditionsVersion);
    199 
    200     AutoCaller autoCaller(this);
    201     if (FAILED(autoCaller.rc())) return autoCaller.rc();
    202 
    203     AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
    204 
    205     HRESULT hr = S_OK;
    206     if (   !mData.mAdditionsVersion.isEmpty()
    207         || !mData.mAdditionsRunLevel > AdditionsRunLevelType_None)
    208         mData.mAdditionsVersion.cloneTo(aAdditionsVersion);
    209     else
    210     {
    211         /*
    212          * If we got back an empty string from GetAdditionsVersion() we either
    213          * really don't have the Guest Additions version yet or the guest is running
    214          * older Guest Additions (< 3.2.0) which don't provide VMMDevReq_ReportGuestInfo2,
    215          * so get the version + revision from the (hopefully) provided guest properties
    216          * instead.
    217          */
    218         Bstr addVersion;
    219         LONG64 u64Timestamp;
    220         Bstr flags;
    221         hr = mParent->machine()->GetGuestProperty(Bstr("/VirtualBox/GuestAdd/Version").raw(),
    222                                                   addVersion.asOutParam(), &u64Timestamp, flags.asOutParam());
    223         if (hr == S_OK)
    224         {
    225             Bstr addRevision;
    226             hr = mParent->machine()->GetGuestProperty(Bstr("/VirtualBox/GuestAdd/Revision").raw(),
    227                                                       addRevision.asOutParam(), &u64Timestamp, flags.asOutParam());
    228             if (   hr == S_OK
    229                 && !addVersion.isEmpty()
    230                 && !addRevision.isEmpty())
    231             {
    232                 /* Some Guest Additions versions had interchanged version + revision values,
    233                  * so check if the version value at least has a dot to identify it and change
    234                  * both values to reflect the right content. */
    235                 if (!Utf8Str(addVersion).contains("."))
    236                 {
    237                     Bstr addTemp = addVersion;
    238                     addVersion = addRevision;
    239                     addRevision = addTemp;
    240                 }
    241 
    242                 /** @todo r=bird: See comment about the space before 'r' in
    243                  *        setAdditionsInfo2. */
    244                 Bstr additionsVersion = BstrFmt("%ls r%ls",
    245                                                 addVersion.raw(), addRevision.raw());
    246                 additionsVersion.cloneTo(aAdditionsVersion);
    247             }
    248             /** @todo r=bird: else: Should not return failure! */
    249         }
     167STDMETHODIMP Guest::COMGETTER(OSTypeId)(BSTR *a_pbstrOSTypeId)
     168{
     169    CheckComArgOutPointerValid(a_pbstrOSTypeId);
     170
     171    AutoCaller autoCaller(this);
     172    HRESULT hrc = autoCaller.rc();
     173    if (SUCCEEDED(hrc))
     174    {
     175        AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     176        if (!mData.mInterfaceVersion.isEmpty())
     177            mData.mOSTypeId.cloneTo(a_pbstrOSTypeId);
    250178        else
    251179        {
    252             /* If getting the version + revision above fails or they simply aren't there
    253              * because of *really* old Guest Additions we only can report the interface
    254              * version to at least have something. */
    255             mData.mInterfaceVersion.cloneTo(aAdditionsVersion);
    256             /** @todo r=bird: hr is still indicating failure! */
     180            /* Redirect the call to IMachine if no additions are installed. */
     181            ComPtr<IMachine> ptrMachine(mParent->machine());
     182            alock.release();
     183            hrc = ptrMachine->COMGETTER(OSTypeId)(a_pbstrOSTypeId);
    257184        }
    258185    }
    259 
    260     return hr;
     186    return hrc;
     187}
     188
     189STDMETHODIMP Guest::COMGETTER(AdditionsRunLevel) (AdditionsRunLevelType_T *aRunLevel)
     190{
     191    AutoCaller autoCaller(this);
     192    if (FAILED(autoCaller.rc())) return autoCaller.rc();
     193
     194    AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     195
     196    *aRunLevel = mData.mAdditionsRunLevel;
     197
     198    return S_OK;
     199}
     200
     201STDMETHODIMP Guest::COMGETTER(AdditionsVersion)(BSTR *a_pbstrAdditionsVersion)
     202{
     203    CheckComArgOutPointerValid(a_pbstrAdditionsVersion);
     204
     205    AutoCaller autoCaller(this);
     206    HRESULT hrc = autoCaller.rc();
     207    if (SUCCEEDED(hrc))
     208    {
     209        AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     210
     211        /*
     212         * Return the ReportGuestInfo2 version info if available.
     213         */
     214        if (   !mData.mAdditionsVersionNew.isEmpty()
     215            || mData.mAdditionsRunLevel <= AdditionsRunLevelType_None)
     216            mData.mAdditionsVersionNew.cloneTo(a_pbstrAdditionsVersion);
     217        else
     218        {
     219            /*
     220             * If we're running older guest additions (< 3.2.0) try get it from
     221             * the guest properties.
     222             */
     223            ComPtr<IMachine> ptrMachine = mParent->machine();
     224            alock.release(); /* No need to hold this during the IPC fun. */
     225
     226            Bstr bstr;
     227            hrc = ptrMachine->GetGuestPropertyValue(Bstr("/VirtualBox/GuestAdd/Version").raw(), bstr.asOutParam());
     228            if (SUCCEEDED(hrc))
     229                bstr.detachTo(a_pbstrAdditionsVersion);
     230            else
     231            {
     232                /* Returning 1.4 is better than nothing. */
     233                alock.acquire();
     234                mData.mInterfaceVersion.cloneTo(a_pbstrAdditionsVersion);
     235                hrc = S_OK;
     236            }
     237        }
     238    }
     239    return hrc;
     240}
     241
     242STDMETHODIMP Guest::COMGETTER(AdditionsRevision)(ULONG *a_puAdditionsRevision)
     243{
     244    CheckComArgOutPointerValid(a_puAdditionsRevision);
     245
     246    AutoCaller autoCaller(this);
     247    HRESULT hrc = autoCaller.rc();
     248    if (SUCCEEDED(hrc))
     249    {
     250        AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     251
     252        /*
     253         * Return the ReportGuestInfo2 version info if available.
     254         */
     255        if (   !mData.mAdditionsVersionNew.isEmpty()
     256            || mData.mAdditionsRunLevel <= AdditionsRunLevelType_None)
     257            *a_puAdditionsRevision = mData.mAdditionsRevision;
     258        else
     259        {
     260            /*
     261             * If we're running older guest additions (< 3.2.0) try get it from
     262             * the guest properties.
     263             */
     264            ComPtr<IMachine> ptrMachine = mParent->machine();
     265            alock.release(); /* No need to hold this during the IPC fun. */
     266
     267            Bstr bstr;
     268            hrc = ptrMachine->GetGuestPropertyValue(Bstr("/VirtualBox/GuestAdd/Revision").raw(), bstr.asOutParam());
     269            if (SUCCEEDED(hrc))
     270            {
     271                Utf8Str str(bstr);
     272                uint32_t uRevision;
     273                int vrc = RTStrToUInt32Full(str.c_str(), 0, &uRevision);
     274                if (vrc == VINF_SUCCESS)
     275                    *a_puAdditionsRevision = uRevision;
     276                else
     277                    hrc = VBOX_E_IPRT_ERROR;
     278            }
     279            if (FAILED(hrc))
     280            {
     281                /* Return 0 if we don't know. */
     282                *a_puAdditionsRevision = 0;
     283                hrc = 0;
     284            }
     285        }
     286    }
     287    return hrc;
    261288}
    262289
     
    725752     * don't have the Additions version set.
    726753     */
    727     if (mData.mAdditionsVersion.isEmpty())
     754    if (mData.mAdditionsVersionNew.isEmpty())
    728755    {
    729756        if (aInterfaceVersion.isEmpty())
     
    760787/**
    761788 * Sets the Guest Additions version information details.
    762  * Gets called by vmmdevUpdateGuestInfo2.
    763789 *
    764  * @param   a_pszVersion            The GuestInfo2 numbers turned into
    765  * @param   a_pszVersionName        This turns out to be the version string +
    766  *                                  beta/alpha/whatever suffix, duplicating info
    767  *                                  passed in @a a_pszVersion.
    768  * @param   a_uRevision             The SVN revision number.
     790 * Gets called by vmmdevUpdateGuestInfo2 and vmmdevUpdateGuestInfo (to clear the
     791 * state).
     792 *
     793 * @param   a_uFullVersion          VBoxGuestInfo2::additionsMajor,
     794 *                                  VBoxGuestInfo2::additionsMinor and
     795 *                                  VBoxGuestInfo2::additionsBuild combined into
     796 *                                  one value by VBOX_FULL_VERSION_MAKE.
     797 *
     798 *                                  When this is 0, it's vmmdevUpdateGuestInfo
     799 *                                  calling to reset the state.
     800 *
     801 * @param   a_pszName               Build type tag and/or publisher tag, empty
     802 *                                  string if neiter of those are present.
     803 * @param   a_uRevision             See VBoxGuestInfo2::additionsRevision.
     804 * @param   a_fFeatures             See VBoxGuestInfo2::additionsFeatures.
    769805 */
    770 void Guest::setAdditionsInfo2(const char *a_pszVersion, const char *a_pszVersionName, uint32_t a_uRevision)
     806void Guest::setAdditionsInfo2(uint32_t a_uFullVersion, const char *a_pszName, uint32_t a_uRevision, uint32_t a_fFeatures)
    771807{
    772808    AutoCaller autoCaller(this);
     
    775811    AutoWriteLock alock(this COMMA_LOCKVAL_SRC_POS);
    776812
    777     /** @todo r=bird: WHY is this code returning "1.2.3 r45678" in one case and
    778      *        "1.2.3r45678" in the else?  Why aren't we doing it the same way as
    779      *        IVirtualBox? One version attribute and one revision attribute, no
    780      *        abigiuos spaces! */
    781     if (*a_pszVersionName != '\0')
    782         /*
    783          * aVersionName could be "x.y.z_BETA1_FOOBAR", so append revision manually to
    784          * become "x.y.z_BETA1_FOOBAR r12345".
    785          */
    786         mData.mAdditionsVersion = BstrFmt("%s r%u", a_pszVersionName, a_uRevision);
    787     else /* aAdditionsVersion is in x.y.zr12345 format. */
    788         mData.mAdditionsVersion = Bstr(a_pszVersion);
    789     //mData.mAdditionsRevision = a_uRevision;
     813    if (a_uFullVersion)
     814    {
     815        mData.mAdditionsVersionNew  = BstrFmt(*a_pszName ? "%u.%u.%u_%s" : "%u.%u.%u",
     816                                              VBOX_FULL_VERSION_GET_MAJOR(a_uFullVersion),
     817                                              VBOX_FULL_VERSION_GET_MINOR(a_uFullVersion),
     818                                              VBOX_FULL_VERSION_GET_BUILD(a_uFullVersion),
     819                                              a_pszName);
     820        mData.mAdditionsVersionFull = a_uFullVersion;
     821        mData.mAdditionsRevision    = a_uRevision;
     822        mData.mAdditionsFeatures    = a_fFeatures;
     823    }
     824    else
     825    {
     826        Assert(!a_fFeatures && !a_uRevision && !*a_pszName);
     827        mData.mAdditionsVersionNew.setNull();
     828        mData.mAdditionsVersionFull = 0;
     829        mData.mAdditionsRevision    = 0;
     830        mData.mAdditionsFeatures    = 0;
     831    }
    790832}
    791833
  • trunk/src/VBox/Main/src-client/VMMDevInterface.cpp

    r39824 r39882  
    188188/**
    189189 * Reports Guest Additions API and OS version.
    190  * Called whenever the Additions issue a guest version report request or the VM is reset.
     190 *
     191 * Called whenever the Additions issue a guest version report request or the VM
     192 * is reset.
    191193 *
    192194 * @param   pInterface          Pointer to this interface.
     
    232234         */
    233235        guest->setAdditionsInfo(Bstr(), guestInfo->osType); /* Clear interface version + OS type. */
    234         guest->setAdditionsInfo2("", "", 0); /* Clear Guest Additions version. */
     236        /** @todo Would be better if GuestImpl.cpp did all this in the above method call
     237         *        while holding down the. */
     238        guest->setAdditionsInfo2(0, "", 0,  0); /* Clear Guest Additions version. */
    235239        guest->setAdditionsStatus(VBoxGuestFacilityType_All,
    236240                                  VBoxGuestFacilityStatus_Inactive,
     
    241245
    242246/**
    243  * Reports the detailed Guest Additions version.
    244  * Called whenever the Additions issue a guest version report request or the VM is reset.
    245  *
    246  * @param   pInterface          Pointer to this interface.
    247  * @param   pGuestInfo          Pointer to Guest Additions information
    248  *                              structure.
    249  * @thread  The emulation thread.
    250  */
    251 DECLCALLBACK(void) vmmdevUpdateGuestInfo2(PPDMIVMMDEVCONNECTOR pInterface, const VBoxGuestInfo2 *pGuestInfo)
    252 {
    253     PDRVMAINVMMDEV pDrv = PDMIVMMDEVCONNECTOR_2_MAINVMMDEV(pInterface);
    254     AssertPtr(pGuestInfo);
     247 * @interface_method_impl{PDMIVMMDEVCONNECTOR,pfnUpdateGuestInfo2}
     248 */
     249DECLCALLBACK(void) vmmdevUpdateGuestInfo2(PPDMIVMMDEVCONNECTOR pInterface, uint32_t uFullVersion,
     250                                          const char *pszName, uint32_t uRevision, uint32_t fFeatures)
     251{
     252    PDRVMAINVMMDEV pDrv = PDMIVMMDEVCONNECTOR_2_MAINVMMDEV(pInterface);
     253    AssertPtr(pszName);
     254    Assert(uFullVersion);
    255255
    256256    /* Store that information in IGuest. */
     
    260260        return;
    261261
    262     if (   pGuestInfo->additionsMajor    != 0
    263         && pGuestInfo->additionsRevision != 0)
    264     {
    265         /** @todo r=bird: See comments on space before 'r' in setAdditionsInfo2! */
    266         char szVersion[32];
    267         RTStrPrintf(szVersion, sizeof(szVersion), "%d.%d.%dr%ld",
    268                     pGuestInfo->additionsMajor,
    269                     pGuestInfo->additionsMinor,
    270                     pGuestInfo->additionsBuild,
    271                     pGuestInfo->additionsRevision);
    272 
    273         pGuest->setAdditionsInfo2(szVersion, pGuestInfo->szName, pGuestInfo->additionsRevision);
    274 
    275         /*
    276          * No need to tell the console interface about the update;
    277          * vmmdevUpdateGuestInfo takes care of that when called as the
    278          * last event in the chain.
    279          */
    280     }
     262    /* Just pass it on... */
     263    pGuest->setAdditionsInfo2(uFullVersion, pszName, uRevision, fFeatures);
     264
     265    /*
     266     * No need to tell the console interface about the update;
     267     * vmmdevUpdateGuestInfo takes care of that when called as the
     268     * last event in the chain.
     269     */
    281270}
    282271
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