Home | History | Annotate | Download | only in Security
      1 /** @file
      2   EFI PEI Core Security services
      3 
      4 Copyright (c) 2006 - 2014, Intel Corporation. All rights reserved.<BR>
      5 This program and the accompanying materials
      6 are licensed and made available under the terms and conditions of the BSD License
      7 which accompanies this distribution.  The full text of the license may be found at
      8 http://opensource.org/licenses/bsd-license.php
      9 
     10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
     11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
     12 
     13 **/
     14 
     15 #include "PeiMain.h"
     16 
     17 
     18 EFI_PEI_NOTIFY_DESCRIPTOR mNotifyList = {
     19    EFI_PEI_PPI_DESCRIPTOR_NOTIFY_DISPATCH | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST,
     20    &gEfiPeiSecurity2PpiGuid,
     21    SecurityPpiNotifyCallback
     22 };
     23 
     24 /**
     25   Initialize the security services.
     26 
     27   @param PeiServices     An indirect pointer to the EFI_PEI_SERVICES table published by the PEI Foundation.
     28   @param OldCoreData     Pointer to the old core data.
     29                          NULL if being run in non-permament memory mode.
     30 
     31 **/
     32 VOID
     33 InitializeSecurityServices (
     34   IN EFI_PEI_SERVICES  **PeiServices,
     35   IN PEI_CORE_INSTANCE *OldCoreData
     36   )
     37 {
     38   if (OldCoreData == NULL) {
     39     PeiServicesNotifyPpi (&mNotifyList);
     40   }
     41   return;
     42 }
     43 
     44 /**
     45 
     46   Provide a callback for when the security PPI is installed.
     47   This routine will cache installed security PPI into PeiCore's private data.
     48 
     49   @param PeiServices        An indirect pointer to the EFI_PEI_SERVICES table published by the PEI Foundation.
     50   @param NotifyDescriptor   The descriptor for the notification event.
     51   @param Ppi                Pointer to the PPI in question.
     52 
     53   @return Always success
     54 
     55 **/
     56 EFI_STATUS
     57 EFIAPI
     58 SecurityPpiNotifyCallback (
     59   IN EFI_PEI_SERVICES           **PeiServices,
     60   IN EFI_PEI_NOTIFY_DESCRIPTOR  *NotifyDescriptor,
     61   IN VOID                       *Ppi
     62   )
     63 {
     64   PEI_CORE_INSTANCE                       *PrivateData;
     65 
     66   //
     67   // Get PEI Core private data
     68   //
     69   PrivateData = PEI_CORE_INSTANCE_FROM_PS_THIS (PeiServices);
     70 
     71   //
     72   // If there isn't a security PPI installed, use the one from notification
     73   //
     74   if (PrivateData->PrivateSecurityPpi == NULL) {
     75     PrivateData->PrivateSecurityPpi = (EFI_PEI_SECURITY2_PPI *)Ppi;
     76   }
     77   return EFI_SUCCESS;
     78 }
     79 
     80 /**
     81   Provide a callout to the security verification service.
     82 
     83   @param PrivateData     PeiCore's private data structure
     84   @param VolumeHandle    Handle of FV
     85   @param FileHandle      Handle of PEIM's ffs
     86   @param AuthenticationStatus Authentication status
     87 
     88   @retval EFI_SUCCESS              Image is OK
     89   @retval EFI_SECURITY_VIOLATION   Image is illegal
     90   @retval EFI_NOT_FOUND            If security PPI is not installed.
     91 **/
     92 EFI_STATUS
     93 VerifyPeim (
     94   IN PEI_CORE_INSTANCE      *PrivateData,
     95   IN EFI_PEI_FV_HANDLE      VolumeHandle,
     96   IN EFI_PEI_FILE_HANDLE    FileHandle,
     97   IN UINT32                 AuthenticationStatus
     98   )
     99 {
    100   EFI_STATUS                      Status;
    101   BOOLEAN                         DeferExection;
    102 
    103   Status = EFI_NOT_FOUND;
    104   if (PrivateData->PrivateSecurityPpi == NULL) {
    105     //
    106     // Check AuthenticationStatus first.
    107     //
    108     if ((AuthenticationStatus & EFI_AUTH_STATUS_IMAGE_SIGNED) != 0) {
    109       if ((AuthenticationStatus & (EFI_AUTH_STATUS_TEST_FAILED | EFI_AUTH_STATUS_NOT_TESTED)) != 0) {
    110         Status = EFI_SECURITY_VIOLATION;
    111       }
    112     }
    113   } else {
    114     //
    115     // Check to see if the image is OK
    116     //
    117     Status = PrivateData->PrivateSecurityPpi->AuthenticationState (
    118                                                 (CONST EFI_PEI_SERVICES **) &PrivateData->Ps,
    119                                                 PrivateData->PrivateSecurityPpi,
    120                                                 AuthenticationStatus,
    121                                                 VolumeHandle,
    122                                                 FileHandle,
    123                                                 &DeferExection
    124                                                 );
    125     if (DeferExection) {
    126       Status = EFI_SECURITY_VIOLATION;
    127     }
    128   }
    129   return Status;
    130 }
    131 
    132 
    133 /**
    134   Verify a Firmware volume.
    135 
    136   @param CurrentFvAddress   Pointer to the current Firmware Volume under consideration
    137 
    138   @retval EFI_SUCCESS       Firmware Volume is legal
    139 
    140 **/
    141 EFI_STATUS
    142 VerifyFv (
    143   IN EFI_FIRMWARE_VOLUME_HEADER  *CurrentFvAddress
    144   )
    145 {
    146   //
    147   // Right now just pass the test.  Future can authenticate and/or check the
    148   // FV-header or other metric for goodness of binary.
    149   //
    150   return EFI_SUCCESS;
    151 }
    152