⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 efibis_basecode.c

📁 Next BIOS Source code : Extensible Firmware Interface
💻 C
📖 第 1 页 / 共 2 页
字号:
/*++

Copyright (c)  1999 - 2002 Intel Corporation. All rights reserved
This software and associated documentation (if any) is furnished
under a license and may only be used or copied in accordance
with the terms of the license. Except as permitted by such
license, no part of this software or documentation may be
reproduced, stored in a retrieval system, or transmitted in any
form or by any means without the express written consent of
Intel Corporation.


Module Name:

    efibis_basecode.c

Abstract:

    Public EFI/BIS functions.


Revision History

--*/

#include <efi.h>
#include <efidriverlib.h>
#include EFI_PROTOCOL_DEFINITION (Bis)
#include <bisBaseCode.h>

static EFI_GUID 		 BISBaseCodeProto=	EFI_BIS_PROTOCOL_GUID;
EFI_BIS_PROTOCOL     *BISBC= NULL;



	//
	// EBDP2DB - Assign EFI_BIS_DATA* to BIS_DATA.
	//		Conversion is safe even if null EFI_BIS_DATA* is presented.
	//
void
EBDP2BD( EFI_BIS_DATA *ebdp,  BIS_DATA* bd)
{
	if ( ebdp == NULL ){
		bd->length= 0;
		bd->data=   0;
	}
	else {
		bd->length= ebdp->Length;
		bd->data=   ebdp->Data;
	}
}

	//
 	// getInstanceData -
 	//		parm:    EFI_BIS_PROTOCOL pointer
	//		returns: address of BISBC_INSTANCEDATA that contains the input parm.
	//				 
BISBC_INSTANCEDATA*
getInstanceData( EFI_BIS_PROTOCOL *bisInterface )
{
	BISBC_INSTANCEDATA *result= NULL;	
	
	if ( bisInterface != NULL )
	{
		result= CR(bisInterface, BISBC_INSTANCEDATA, bisInterface, BBCIDSIG);
		
		//structure at computed address should contain structure length
		//and contain signature.
		if ( result->sizeOfThis != sizeof(BISBC_INSTANCEDATA)
		||   result->Signature  != BBCIDSIG )
		{
			result= NULL;
		}
						
	}
	
	return result;

}


	//
	// EFI_BIS_Initialize()
	//

EFI_STATUS
EFI_BIS_Initialize(
    IN     EFI_BIS_PROTOCOL        *This,             //this
    OUT    BIS_APPLICATION_HANDLE  *AppHandle,        //Application handle.
    IN OUT EFI_BIS_VERSION         *InterfaceVersion, //ver needed/available.
    IN     EFI_BIS_DATA            *TargetAddress     //Address of BIS platform.
    )
{
	BIS_INIT_PARMS 	   initParms;
	BIS_INIT_PARMS	   *parmBlock= &initParms;
    BIS_APPINFO_PTR    appInfo;
    NVM_AREA_ID        bisNvmAreaId= NVM_BIS_AREA_ID;
    UINT32             maxSize;
    BIS_STATUS         addOK;
	BISBC_INSTANCEDATA *bisGlobal;
	COLLECTION		   *appInfoTrackingCollection;

	//Print(L"Bis_Initialize called\n");

	if ( This == NULL || AppHandle == NULL
	||   InterfaceVersion == NULL  )
	{
		return EFI_DEVICE_ERROR;
	}


	//
	// Do parm block validation. Almost verbatim from BIS legacy client.
	//
	bisGlobal=  getInstanceData( This );
	if ( bisGlobal == NULL )
	{
		return EFI_DEVICE_ERROR;
	}
	
	//Only one BIS user at a time.
	if ( bisGlobal->bisInUse == BIS_TRUE ){
	    return EFI_OUT_OF_RESOURCES;
    }
	
		
	appInfoTrackingCollection= bisGlobal->appInfoTrackingCollection;

	//Convert EFI_BIS parms to BIS parm block.
	EfiZeroMem( &initParms, sizeof(initParms) );
	initParms.sizeOfStruct= 	sizeof(initParms);
	initParms.interfaceVersion.major= InterfaceVersion->Major;
	initParms.interfaceVersion.minor= InterfaceVersion->Minor;

  EBDP2BD( TargetAddress,  &initParms.targetAddress);


    //Version negotiation. As of Sept. 98 there is only one
    //version. If you ask for anything else, we fail you.
    //In the future we'll need to determine if the requested
    //version is compatible with the available version.
    if (parmBlock->interfaceVersion.major != BIS_CURRENT_VERSION_MAJOR)
    {
        //pass back actual numbers.
        InterfaceVersion->Major= BIS_CURRENT_VERSION_MAJOR;
        InterfaceVersion->Minor= BIS_CURRENT_VERSION_MINOR;

        return EFI_INCOMPATIBLE_VERSION;
    }

    //pass back actual minor version.
    InterfaceVersion->Minor= BIS_CURRENT_VERSION_MINOR;


    //Allocate and initialize appInfo structure and CSSM structure.
    parmBlock->appHandle= BIS_NULL;
    appInfo= (BIS_APPINFO_PTR) x_malloc( sizeof(BIS_APPINFO) + sizeof(APP_CSSMINFO));
    if (appInfo)
    {

        appInfo->SizeOfStruct= sizeof(BIS_APPINFO);

        //Add new appinfo struct to BIS' collection.
        addOK= COL_AddElement( appInfoTrackingCollection, (UINTN)appInfo );

        //create the apps memory tracking collection.
        if (addOK)
        {
            appInfo->memoryAllocations= COL_New( BIS_INIT_COLLECTION_SIZE
            ,  BIS_INIT_COLLECTION_INCR );
        }

        //Bail on memory allocation failures.
        if (addOK == BIS_FALSE || appInfo->memoryAllocations == NULL )
        {
            gBS->FreePool( appInfo );
            return EFI_OUT_OF_RESOURCES;
        }

        //Make appInfo->pCssmInfo point to it's piece of the allocation;
        appInfo->pCssmInfo= (APP_CSSMINFO_PTR) ( appInfo + 1);

		//Point to same instance data that interface structure points to.
		appInfo->efiInstanceData= bisGlobal;
    }
    else
    {
        return EFI_OUT_OF_RESOURCES;
    }

    //return the appinfo struct address.
    parmBlock->appHandle= (BIS_APPLICATION_HANDLE)appInfo;


    //Initialize the crypto and manifest service subsys.
    parmBlock->returnValue = (UINT32)PSD_InitializeApp( appInfo, appInfo->pCssmInfo );
    if ( parmBlock->returnValue != BIS_OK )
    {
        COL_Destroy( appInfo->memoryAllocations );
        gBS->FreePool( appInfo );
        return parmBlock->returnValue;
    }


    //Open our NVM (non volatile mem area).
    appInfo->nvmHandle= NVM_Open( appInfo, &bisNvmAreaId, &maxSize);
    if ( appInfo->nvmHandle == BIS_NULL)
    {

        //this not currently fatal.
        return EFI_DEVICE_ERROR;
    }


	bisGlobal->bisInUse=   BIS_TRUE;
	*AppHandle= parmBlock->appHandle;
    return EFI_SUCCESS;

}	//End EFI_BIS_Initialize



	//
	// EFI_BIS_FREE()
	//

EFI_STATUS
EFI_BIS_Free(
    IN BIS_APPLICATION_HANDLE  AppHandle,      //From Initialize( ).
    IN EFI_BIS_DATA            *ToFree         //[in]  BIS_DATA being freed.
	)
{
	EFI_STATUS      rc= EFI_SUCCESS;
  BIS_APPINFO_PTR appInfo;


    //Extract BIS_APPINFO_PTR
    appInfo= CAST_APP_HANDLE(AppHandle);

    //Check apphandle validity
    if ( appInfo == BIS_NULL  || (!IS_APPINFO_VALID(appInfo)))
    {
        rc= BIS_BAD_APPHANDLE;
    }

	if ( ToFree == NULL )
	{
		return EFI_INVALID_PARAMETER;
	}

    //Free memory and remove from tracking collection in 'appInfo'.
	if ( rc == EFI_SUCCESS )
	{
	    if ( !MEM_free( appInfo, ToFree ) )
	    {
	        rc= EFI_INVALID_PARAMETER;
	    }
	}

    //success.
	return rc;

}


	//
	//	 EFI_BIS_Shutdown()
	//

EFI_STATUS
EFI_BIS_Shutdown(
    IN BIS_APPLICATION_HANDLE  AppHandle       // From Initialize( ).
	)
{
	BIS_SHUTDOWN_PARMS shutParms;

    BIS_APPINFO_PTR  appInfo;
    COLLECTION      *col;
    UINTN            colIx;
    UINTN            element;
    void            *memptr;
    EFI_STATUS       rv;

	BISBC_INSTANCEDATA  *bisGlobal;
	COLLECTION			*appInfoTrackingCollection;


	//Shutdown logic is almost verbatin from BIS legacy implementation.

    //Extract BIS_APPINFO_PTR
    appInfo= 	CAST_APP_HANDLE(AppHandle);


    //Check apphandle validity
    if ( appInfo == BIS_NULL  || (!IS_APPINFO_VALID(appInfo))){
        return EFI_NO_MAPPING;
    }

	bisGlobal=  				appInfo->efiInstanceData;
	appInfoTrackingCollection=  bisGlobal->appInfoTrackingCollection;


	EfiZeroMem( &shutParms, sizeof(shutParms) );
	shutParms.sizeOfStruct= sizeof(shutParms);
	shutParms.appHandle=    AppHandle;


    //Close the non-volative memory
    rv= NVM_Close( appInfo, appInfo->nvmHandle );
    if ( rv != EFI_SUCCESS)
    {
    	bisGlobal->bisInUse= BIS_FALSE;
      return rv;
    }


    //Close CSSM subsystem.
    PSD_Shutdown( appInfo->pCssmInfo );


    //Interate over the collection appInfo->memoryAllocations,
    //Free any memory that this app failed to free for itself
    col= appInfo->memoryAllocations;


    //Processing highest to lowest index, avoids compaction in COLLECTION.
    colIx= COL_GetCount( col );
    while ( colIx )       //NOTE: while condition contains an assignement!
    {
        colIx -= 1;             //adjust for zero origin index.

        if ( COL_ElementAt( col, colIx, &element ) )
        {
            memptr= (void*)element;
            gBS->FreePool( memptr );                //free the memory
            COL_RemoveElementAt( col, colIx);   //delete collection element.
        }

        colIx= COL_GetCount( col );
    }

    // Delete the collection object
    COL_Destroy( col );


    //Destroy appinfo object and remove from BIS' collection.
    gBS->FreePool( appInfo );
    COL_RemoveElement( appInfoTrackingCollection, (UINTN)appInfo );

   	bisGlobal->bisInUse= BIS_FALSE;
    return EFI_SUCCESS;

}


	//
	// EFI_BIS_GetBootObjectAuthorizationCertificate()
	//


EFI_STATUS
EFI_BIS_GetBootObjectAuthorizationCertificate(
    IN  BIS_APPLICATION_HANDLE  AppHandle,      // From Initialize( ).
    OUT EFI_BIS_DATA            **Certificate   // Pointer to certificate.
	)
{
	BIS_GBOAC_PARMS 	gboacParms;
	BIS_GBOAC_PARMS 	*parmBlock= &gboacParms;

  BIS_APPINFO_PTR 	appInfo;
  BIS_DATA_PTR    	boaCert;
  EFI_STATUS      	status;
	EFI_STATUS			persistSt;
  UINT32          	certLength;
  UINT32          	flashLength;
	BISBC_INSTANCEDATA  *bisGlobal;


    //Extract BIS_APPINFO_PTR
    appInfo= CAST_APP_HANDLE(AppHandle);

    //Check parms.
    if ( appInfo == BIS_NULL  || (!IS_APPINFO_VALID(appInfo))){
        return EFI_NO_MAPPING;
    }
	if ( Certificate == NULL )
	{
		return EFI_INVALID_PARAMETER;
	}

	bisGlobal=  appInfo->efiInstanceData;

	EfiZeroMem( &gboacParms, sizeof(gboacParms) );
	gboacParms.sizeOfStruct= sizeof(gboacParms);
	gboacParms.appHandle=    AppHandle;

    //Attempt to read the certificate length field from NVM.
    status= NVM_Read( appInfo->nvmHandle
        , (UINT8 *)&certLength
        , sizeof(certLength)
        , GET_NVM_FIELD_OFFSET( byteLengthOfBOACert )
        );
    if ( status != EFI_SUCCESS ) {
        return status;
    }
    else if ( certLength == 0 ){
        return EFI_NOT_FOUND;
    }

    //Is certLength reasonable? If too big for available area
    //assume that the plat cert is not configured.
    persistSt= bisGlobal->Persist->GetLength(
					bisGlobal->Persist, &flashLength, BIS_NULL );

	if ( persistSt != EFI_SUCCESS ){
		return EFI_NOT_FOUND;
	}

    flashLength= flashLength - sizeof(BIS_BOOLEAN); //updateCheckFlag size
    flashLength= flashLength
			   - GET_NVM_FIELD_SIZE( bootObjectAuthorizationUpdateCount );
    flashLength= flashLength - sizeof(certLength);

    if ( certLength > flashLength)
    {
        return EFI_NOT_FOUND;
    }


    //Create structure to hold the certificate.
    boaCert= parmBlock->certificate=
    MEM_allocBisData( appInfo, certLength );
    if ( boaCert == BIS_NULL) {
        return EFI_OUT_OF_RESOURCES;
    }


    //Attempt to read the certificate from NVM.
    status= NVM_Read( appInfo->nvmHandle
        , (UINT8 *)boaCert->data
        , certLength
        , GET_NVM_FIELD_OFFSET( bootObjectAuthorizationCertificate )
        );

    //Delete the data block if read failed.
    if (status != EFI_SUCCESS){
        MEM_free( appInfo, boaCert);
        parmBlock->certificate=  BIS_NULL;
    }

	  *Certificate= (EFI_BIS_DATA*)parmBlock->certificate;
    return status;

}


	//
	//	EFI_BIS_VerifyBootObject( )
	//

EFI_STATUS
EFI_BIS_VerifyBootObject(
    IN  BIS_APPLICATION_HANDLE AppHandle,    // From Initialize( ).
    IN  EFI_BIS_DATA           *Credentials, // Verification signed manifest.
    IN  EFI_BIS_DATA           *DataObject,  // Boot object to verify.
    OUT BOOLEAN                *IsVerified   // Result of verifcation.
	)
{
	BIS_VBO_PARMS   vboParms;
	BIS_STATUS      rc;
    BIS_APPINFO_PTR appInfo;




    //Extract BIS_APPINFO_PTR
    appInfo= CAST_APP_HANDLE(AppHandle);

    //Check apphandle validity
    if ( appInfo == BIS_NULL  || (!IS_APPINFO_VALID(appInfo))){
        return EFI_NO_MAPPING;
    }

	if ( Credentials == NULL || DataObject == NULL || IsVerified == NULL)
	{
		return EFI_INVALID_PARAMETER;
	}

	//Setup Parm Block
	EfiZeroMem( &vboParms, sizeof(vboParms) );
	vboParms.sizeOfStruct= sizeof(vboParms);
	vboParms.appHandle=	   AppHandle;

	EBDP2BD( Credentials,  &vboParms.credentials);
	EBDP2BD( DataObject,  &vboParms.dataObject);

    rc= Core_VerifyBootObject( appInfo, appInfo->pCssmInfo, &vboParms );
	*IsVerified= (BOOLEAN)((vboParms.isVerified == BIS_TRUE) ? TRUE:FALSE);

	return mapBisToEfi(rc);

}



	//
	// EFI_BIS_GetBootObjectAuthorizationCheckFlag()
	//

EFI_STATUS
EFI_BIS_GetBootObjectAuthorizationCheckFlag(
    IN  BIS_APPLICATION_HANDLE  AppHandle,        // From Initialize( ).

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -