VirtualBox

Changeset 91434 in vbox for trunk/src/VBox


Ignore:
Timestamp:
Sep 28, 2021 11:56:50 AM (3 years ago)
Author:
vboxsync
Message:

Main/NvramStoreImpl: Implement API to initialize the UEFI variable store and some other fixes, bugref:9580

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

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Main/include/NvramStoreImpl.h

    r91396 r91434  
    7171    void i_updateNonVolatileStorageFile(const com::Utf8Str &aNonVolatileStorageFile);
    7272
    73     int i_loadStore(void);
     73    int i_loadStore(const char *pszPath);
    7474    int i_loadStoreFromTar(RTVFSFSSTREAM hVfsFssTar);
    7575    int i_saveStore(void);
  • trunk/src/VBox/Main/src-all/NvramStoreImpl.cpp

    r91396 r91434  
    265265
    266266    unconst(m->pParent) = NULL;
     267#ifndef VBOX_COM_INPROC
     268    unconst(m->pUefiVarStore) = NULL;
     269#endif
    267270
    268271    /* Delete the NVRAM content. */
     
    313316    if (FAILED(adep.rc())) return adep.rc();
    314317
     318    Utf8Str strPath;
     319    NvramStore::getNonVolatileStorageFile(strPath);
     320
    315321    /* We need a write lock because of the lazy initialization. */
    316322    AutoWriteLock wlock(this COMMA_LOCKVAL_SRC_POS);
    317323
    318     /* Check if we have to create the UEFI variabel store object */
     324    /* Check if we have to create the UEFI variable store object */
    319325    HRESULT hrc = S_OK;
    320326    if (!m->pUefiVarStore)
     
    323329        if (!m->bd->mapNvram.size())
    324330        {
    325             int vrc = i_loadStore();
     331            int vrc = i_loadStore(strPath.c_str());
    326332            if (RT_FAILURE(vrc))
    327333                hrc = setError(E_FAIL, tr("Loading the NVRAM store failed (%Rrc)\n"), vrc);
     
    351357
    352358    if (SUCCEEDED(hrc))
     359    {
    353360        m->pUefiVarStore.queryInterfaceTo(aUefiVarStore.asOutParam());
     361
     362        /* Mark the NVRAM store as potentially modified. */
     363        m->pParent->i_setModified(Machine::IsModified_NvramStore);
     364    }
    354365
    355366    return hrc;
     
    363374HRESULT NvramStore::initUefiVariableStore(ULONG aSize)
    364375{
     376#ifndef VBOX_COM_INPROC
     377    if (aSize != 0)
     378        return setError(E_NOTIMPL, tr("Supporting another NVRAM size apart from the default one is not supported right now"));
     379
     380    /* the machine needs to be mutable */
     381    AutoMutableStateDependency adep(m->pParent);
     382    if (FAILED(adep.rc())) return adep.rc();
     383
     384    Utf8Str strPath;
     385    NvramStore::getNonVolatileStorageFile(strPath);
     386
     387    /* We need a write lock because of the lazy initialization. */
     388    AutoWriteLock wlock(this COMMA_LOCKVAL_SRC_POS);
     389
     390    /* Load the NVRAM file first if it isn't already. */
     391    HRESULT hrc = S_OK;
     392    if (!m->bd->mapNvram.size())
     393    {
     394        int vrc = i_loadStore(strPath.c_str());
     395        if (RT_FAILURE(vrc))
     396            hrc = setError(E_FAIL, tr("Loading the NVRAM store failed (%Rrc)\n"), vrc);
     397    }
     398
     399    if (SUCCEEDED(hrc))
     400    {
     401        int vrc = VINF_SUCCESS;
     402        RTVFSFILE hVfsUefiVarStore = NIL_RTVFSFILE;
     403        NvramStoreIter it = m->bd->mapNvram.find("efi/nvram");
     404        if (it != m->bd->mapNvram.end())
     405            hVfsUefiVarStore = it->second;
     406        else
     407        {
     408            /* Create a new file. */
     409            vrc = RTVfsMemFileCreate(NIL_RTVFSIOSTREAM, 0 /*cbEstimate*/, &hVfsUefiVarStore);
     410            if (RT_SUCCESS(vrc))
     411            {
     412                /** @todo The size is hardcoded to match what the firmware image uses right now which is a gross hack... */
     413                vrc = RTVfsFileSetSize(hVfsUefiVarStore, 546816, RTVFSFILE_SIZE_F_NORMAL);
     414                if (RT_SUCCESS(vrc))
     415                    m->bd->mapNvram["efi/nvram"] = hVfsUefiVarStore;
     416                else
     417                    RTVfsFileRelease(hVfsUefiVarStore);
     418            }
     419        }
     420
     421        if (RT_SUCCESS(vrc))
     422        {
     423            vrc = RTEfiVarStoreCreate(hVfsUefiVarStore, 0 /*offStore*/, 0 /*cbStore*/, RTEFIVARSTORE_CREATE_F_DEFAULT, 0 /*cbBlock*/,
     424                                      NULL /*pErrInfo*/);
     425            if (RT_FAILURE(vrc))
     426                return setError(E_FAIL, tr("Failed to initialize the UEFI variable store (%Rrc)"), vrc);
     427        }
     428        else
     429            return setError(E_FAIL, tr("Failed to initialize the UEFI variable store (%Rrc)"), vrc);
     430
     431        m->pParent->i_setModified(Machine::IsModified_NvramStore);
     432    }
     433
     434    return hrc;
     435#else
    365436    NOREF(aSize);
    366437    return E_NOTIMPL;
     438#endif
    367439}
    368440
     
    455527 * @returns IPRT status code.
    456528 */
    457 int NvramStore::i_loadStore(void)
     529int NvramStore::i_loadStore(const char *pszPath)
    458530{
    459531    uint64_t cbStore = 0;
    460     int rc = RTFileQuerySizeByPath(m->bd->strNvramPath.c_str(), &cbStore);
     532    int rc = RTFileQuerySizeByPath(pszPath, &cbStore);
    461533    if (RT_SUCCESS(rc))
    462534    {
     
    473545             */
    474546            RTVFSIOSTREAM hVfsIosNvram;
    475             rc = RTVfsIoStrmOpenNormal(m->bd->strNvramPath.c_str(), RTFILE_O_OPEN | RTFILE_O_READ | RTFILE_O_DENY_NONE,
     547            rc = RTVfsIoStrmOpenNormal(pszPath, RTFILE_O_OPEN | RTFILE_O_READ | RTFILE_O_DENY_NONE,
    476548                                       &hVfsIosNvram);
    477549            if (RT_SUCCESS(rc))
     
    517589                    }
    518590                    else
    519                         LogRel(("Opening the UEFI variable store '%s' failed with %Rrc\n", m->bd->strNvramPath.c_str(), rc));
     591                        LogRel(("Opening the UEFI variable store '%s' failed with %Rrc\n", pszPath, rc));
    520592
    521593                    RTVfsFileRelease(hVfsFileNvram);
    522594                }
    523595                else
    524                     LogRel(("Failed to memorize NVRAM store '%s' with %Rrc\n", m->bd->strNvramPath.c_str(), rc));
     596                    LogRel(("Failed to memorize NVRAM store '%s' with %Rrc\n", pszPath, rc));
    525597
    526598                RTVfsIoStrmRelease(hVfsIosNvram);
    527599            }
    528600            else
    529                 LogRelMax(10, ("NVRAM store '%s' couldn't be opened with %Rrc\n", m->bd->strNvramPath.c_str(), rc));
     601                LogRelMax(10, ("NVRAM store '%s' couldn't be opened with %Rrc\n", pszPath, rc));
    530602        }
    531603        else
    532604            LogRelMax(10, ("NVRAM store '%s' exceeds limit of %u bytes, actual size is %u\n",
    533                            m->bd->strNvramPath.c_str(), _1M, cbStore));
     605                           pszPath, _1M, cbStore));
    534606    }
    535607    else if (rc == VERR_FILE_NOT_FOUND) /* Valid for the first run where no NVRAM file is there. */
     
    608680        AssertRC(rc); RT_NOREF(rc);
    609681
     682        Utf8Str strTmp;
     683        NvramStore::getNonVolatileStorageFile(strTmp);
     684
    610685        RTVFSIOSTREAM hVfsIosDst;
    611         rc = RTVfsIoStrmOpenNormal(m->bd->strNvramPath.c_str(), RTFILE_O_CREATE_REPLACE | RTFILE_O_WRITE | RTFILE_O_DENY_NONE,
     686        rc = RTVfsIoStrmOpenNormal(strTmp.c_str(), RTFILE_O_CREATE_REPLACE | RTFILE_O_WRITE | RTFILE_O_DENY_NONE,
    612687                                   &hVfsIosDst);
    613688        if (RT_SUCCESS(rc))
     
    664739 *  @param data Configuration settings.
    665740 *
    666  *  @note Locks this object for reading.
     741 *  @note Locks this object for writing.
    667742 */
    668743HRESULT NvramStore::i_saveSettings(settings::NvramSettings &data)
     
    671746    AssertComRCReturnRC(autoCaller.rc());
    672747
    673     AutoReadLock alock(this COMMA_LOCKVAL_SRC_POS);
     748    AutoWriteLock wlock(this COMMA_LOCKVAL_SRC_POS);
    674749
    675750    data.strNvramPath = m->bd->strNvramPath;
     751
     752    unconst(m->pUefiVarStore) = NULL;
     753
     754    int vrc = i_saveStore();
     755    if (RT_FAILURE(vrc))
     756        return setError(E_FAIL, tr("Failed to save the NVRAM content to disk (%Rrc)"), vrc);
    676757
    677758    return S_OK;
     
    9341015    if (cRefs == 1)
    9351016    {
    936         int rc = pThis->pNvramStore->i_loadStore();
     1017        int rc = pThis->pNvramStore->i_loadStore(pThis->pNvramStore->m->bd->strNvramPath.c_str());
    9371018        if (RT_FAILURE(rc))
    9381019        {
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