From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: mx.groups.io; dkim=missing; spf=pass (domain: intel.com, ip: 134.134.136.20, mailfrom: christopher.j.zurcher@intel.com) Received: from mga02.intel.com (mga02.intel.com [134.134.136.20]) by groups.io with SMTP; Fri, 16 Aug 2019 13:22:19 -0700 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from orsmga003.jf.intel.com ([10.7.209.27]) by orsmga101.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 16 Aug 2019 13:22:19 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.64,394,1559545200"; d="scan'208";a="179772350" Received: from fmsmsx107.amr.corp.intel.com ([10.18.124.205]) by orsmga003.jf.intel.com with ESMTP; 16 Aug 2019 13:22:18 -0700 Received: from fmsmsx161.amr.corp.intel.com (10.18.125.9) by fmsmsx107.amr.corp.intel.com (10.18.124.205) with Microsoft SMTP Server (TLS) id 14.3.439.0; Fri, 16 Aug 2019 13:22:18 -0700 Received: from crsmsx102.amr.corp.intel.com (172.18.63.137) by FMSMSX161.amr.corp.intel.com (10.18.125.9) with Microsoft SMTP Server (TLS) id 14.3.439.0; Fri, 16 Aug 2019 13:22:18 -0700 Received: from crsmsx103.amr.corp.intel.com ([169.254.4.51]) by CRSMSX102.amr.corp.intel.com ([169.254.2.72]) with mapi id 14.03.0439.000; Fri, 16 Aug 2019 14:22:14 -0600 From: "Zurcher, Christopher J" To: "Wu, Hao A" , "devel@edk2.groups.io" CC: "Kinney, Michael D" , "Yao, Jiewen" , "Wang, Jian J" , "Gao, Liming" Subject: Re: [edk2-devel] [PATCH v4 2/2] MdeModulePkg/ScsiDiskDxe: Support Storage Security Command Protocol Thread-Topic: [edk2-devel] [PATCH v4 2/2] MdeModulePkg/ScsiDiskDxe: Support Storage Security Command Protocol Thread-Index: AQHVIYxtW0lgrc6hkUGwrA1qS2jib6afdIKwgF8koWA= Date: Fri, 16 Aug 2019 20:22:14 +0000 Message-ID: <8EE4873E19344F4DA986A2AC15D512AE4A477A58@CRSMSX103.amr.corp.intel.com> References: <20190613020454.19324-1-christopher.j.zurcher@intel.com> <20190613020454.19324-3-christopher.j.zurcher@intel.com> In-Reply-To: Accept-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: x-titus-metadata-40: eyJDYXRlZ29yeUxhYmVscyI6IiIsIk1ldGFkYXRhIjp7Im5zIjoiaHR0cDpcL1wvd3d3LnRpdHVzLmNvbVwvbnNcL0ludGVsMyIsImlkIjoiYTlkZjBjMmQtMGY3My00MzgwLWEzNTQtNjI4N2FmYTQwYzVkIiwicHJvcHMiOlt7Im4iOiJDVFBDbGFzc2lmaWNhdGlvbiIsInZhbHMiOlt7InZhbHVlIjoiQ1RQX05UIn1dfV19LCJTdWJqZWN0TGFiZWxzIjpbXSwiVE1DVmVyc2lvbiI6IjE3LjEwLjE4MDQuNDkiLCJUcnVzdGVkTGFiZWxIYXNoIjoiXC9HNjJ6QXAyZURnbmpHNzUyd25mcFg2OGJOSFFoaFp1SFFpYzlPT09TcjBXVm9VV2IrSVcyM1ZnbkVcL0M5cUFYIn0= x-ctpclassification: CTP_NT dlp-product: dlpe-windows dlp-version: 11.2.0.6 dlp-reaction: no-action x-originating-ip: [172.18.205.10] MIME-Version: 1.0 Return-Path: christopher.j.zurcher@intel.com Content-Language: en-US Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: quoted-printable Hao, Why will this cause CDROM devices to fail to be recognized? If they requir= e a capacity read, I can change the MustReadCapacity flag to TRUE. On subse= quent media change, the sense key parsing will set Action to ACTION_READ_CA= PACITY so that case is covered as well. Is there a reason the MustReadCapac= ity flag was originally set to FALSE for CDROM devices? With the default ac= tion being to read capacity anyway, the existing implementation seems to ma= ke the flag mostly useless. I have implemented the rest of the suggestions. Thanks, Christopher Zurcher -----Original Message----- From: Wu, Hao A=20 Sent: Monday, June 17, 2019 19:12 To: devel@edk2.groups.io; Zurcher, Christopher J Cc: Kinney, Michael D ; Yao, Jiewen ; Wang, Jian J ; Gao, Liming Subject: RE: [edk2-devel] [PATCH v4 2/2] MdeModulePkg/ScsiDiskDxe: Support= Storage Security Command Protocol > -----Original Message----- > From: devel@edk2.groups.io [mailto:devel@edk2.groups.io] On Behalf Of > Zurcher, Christopher J > Sent: Thursday, June 13, 2019 10:05 AM > To: devel@edk2.groups.io > Cc: Kinney, Michael D; Yao, Jiewen; Wang, Jian J; Gao, Liming > Subject: [edk2-devel] [PATCH v4 2/2] MdeModulePkg/ScsiDiskDxe: Support > Storage Security Command Protocol >=20 > This patch implements the EFI_STORAGE_SECURITY_COMMAND_PROTOCOL > in the > ScsiDiskDxe driver. >=20 > Support is currently limited to the RPMB Well-known LUN for UFS devices. Hello, Some general level comments: 1. CDROM device issue This patch will bring an issue to the CDROM devices that CD/DVD will not be recognized properly. I think the cause of the issue is the relocation of the below logic: ScsiDiskDevice->BlkIo.Media->MediaPresent =3D TRUE; from GetMediaInfo() to ScsiDiskTestUnitReady(). It will lead to the read capacity command being skipped for CDROM devices, which results into the LastBlock for the device equals to 0. We may need to find out a better approach to handle the case for UFS RPMB. 2. Split this patch into three commits Besides adding the Storage Security Command Protocol support in ScsiDisk driver, the patch also: * Updates the ScsiBus driver to recognize the Well known logical unit * Updates the UfsPassThruDxe driver to expose the RPMB WLUN Please help to split the patch into 3 separate commits. 3. Updates for the BlockIO(2) services For functions ScsiDiskReadBlocks(Ex) & ScsiDiskWriteBlocks(Ex), below code= s are added for the dummy BlockIO(2) protocol instance on the UFS RPMB Lun: if (BlockSize =3D=3D 0) { Status =3D EFI_UNSUPPORTED; goto Done; } I suggest to use status 'EFI_DEVICE_ERROR' for such case, since 'EFI_UNSUPPORTED' is not listed as an expected return status in the UEFI spec. 4. Reinstallation of the EFI_STORAGE_SECURITY_COMMAND_PROTOCOL For the reinstallation of the SSC protocol to handle media change, I saw this is only handled within ScsiDiskReceiveData() & ScsiDiskSendData(). The below functions should be considered as well: ScsiDiskReadBlocks(Ex) ScsiDiskWriteBlocks(Ex) ScsiDiskFlushBlocksEx ScsiDiskEraseBlocks Some inline comments below: >=20 > Cc: Michael D Kinney > Cc: Jiewen Yao > Cc: Jian J Wang > Cc: Liming Gao > Signed-off-by: Christopher J Zurcher > --- > MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf | 3 +- > MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.h | 171 ++++++- > MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBus.c | 5 +- > MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.c | 522 > +++++++++++++++++++- > MdeModulePkg/Bus/Ufs/UfsPassThruDxe/UfsPassThru.c | 19 +- > 5 files changed, 698 insertions(+), 22 deletions(-) >=20 > diff --git a/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf > b/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf > index 5500d828e9..40818e669b 100644 > --- a/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf > +++ b/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf > @@ -3,7 +3,7 @@ > # It detects the SCSI disk media and installs Block I/O and Block I/O2= Protocol > on > # the device handle. > # > -# Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved. > +# Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved. > # SPDX-License-Identifier: BSD-2-Clause-Patent > # > ## > @@ -52,6 +52,7 @@ > gEfiBlockIoProtocolGuid ## BY_START > gEfiBlockIo2ProtocolGuid ## BY_START > gEfiEraseBlockProtocolGuid ## BY_START > + gEfiStorageSecurityCommandProtocolGuid ## BY_START > gEfiScsiIoProtocolGuid ## TO_START > gEfiScsiPassThruProtocolGuid ## TO_START > gEfiExtScsiPassThruProtocolGuid ## TO_START > diff --git a/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.h > b/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.h > index 42c0aaaa95..2d8679ec6f 100644 > --- a/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.h > +++ b/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.h > @@ -1,7 +1,7 @@ > /** @file > Header file for SCSI Disk Driver. >=20 > -Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.
> +Copyright (c) 2004 - 2019, Intel Corporation. All rights reserved.
> SPDX-License-Identifier: BSD-2-Clause-Patent >=20 > **/ > @@ -22,6 +22,7 @@ SPDX-License-Identifier: BSD-2-Clause-Patent > #include > #include > #include > +#include >=20 >=20 > #include > @@ -38,6 +39,10 @@ SPDX-License-Identifier: BSD-2-Clause-Patent >=20 > #define IS_DEVICE_FIXED(a) (a)->FixedDevice ? 1 : 0 >=20 > +#define IS_ALIGNED(addr, size) (((UINTN) (addr) & (size - 1)) =3D=3D= 0) > + > +#define UFS_WLUN_RPMB 0xC4 > + > typedef struct { > UINT32 MaxLbaCnt; > UINT32 MaxBlkDespCnt; > @@ -51,6 +56,8 @@ typedef struct { >=20 > EFI_HANDLE Handle; >=20 > + EFI_STORAGE_SECURITY_COMMAND_PROTOCOL StorageSecurity; > + > EFI_BLOCK_IO_PROTOCOL BlkIo; > EFI_BLOCK_IO2_PROTOCOL BlkIo2; > EFI_BLOCK_IO_MEDIA BlkIoMedia; > @@ -95,6 +102,7 @@ typedef struct { > #define SCSI_DISK_DEV_FROM_BLKIO(a) CR (a, SCSI_DISK_DEV, BlkIo, > SCSI_DISK_DEV_SIGNATURE) > #define SCSI_DISK_DEV_FROM_BLKIO2(a) CR (a, SCSI_DISK_DEV, BlkIo2, > SCSI_DISK_DEV_SIGNATURE) > #define SCSI_DISK_DEV_FROM_ERASEBLK(a) CR (a, SCSI_DISK_DEV, > EraseBlock, SCSI_DISK_DEV_SIGNATURE) > +#define SCSI_DISK_DEV_FROM_STORSEC(a) CR (a, SCSI_DISK_DEV, > StorageSecurity, SCSI_DISK_DEV_SIGNATURE) >=20 > #define SCSI_DISK_DEV_FROM_DISKINFO(a) CR (a, SCSI_DISK_DEV, > DiskInfo, SCSI_DISK_DEV_SIGNATURE) >=20 > @@ -638,6 +646,151 @@ ScsiDiskEraseBlocks ( > ); >=20 >=20 > +/** > + Send a security protocol command to a device that receives data and/o= r > the result > + of one or more commands sent by SendData. > + > + The ReceiveData function sends a security protocol command to the giv= en > MediaId. > + The security protocol command sent is defined by SecurityProtocolId a= nd > contains > + the security protocol specific data SecurityProtocolSpecificData. The > function > + returns the data from the security protocol command in PayloadBuffer. > + > + For devices supporting the SCSI command set, the security protocol > command is sent > + using the SECURITY PROTOCOL IN command defined in SPC-4. > + > + If PayloadBufferSize is too small to store the available data from th= e > security > + protocol command, the function shall copy PayloadBufferSize bytes int= o > the > + PayloadBuffer and return EFI_WARN_BUFFER_TOO_SMALL. > + > + If PayloadBuffer or PayloadTransferSize is NULL and PayloadBufferSize= is > non-zero, > + the function shall return EFI_INVALID_PARAMETER. > + > + If the given MediaId does not support security protocol commands, the > function shall > + return EFI_UNSUPPORTED. If there is no media in the device, the funct= ion > returns > + EFI_NO_MEDIA. If the MediaId is not the ID for the current media in t= he > device, > + the function returns EFI_MEDIA_CHANGED. > + > + If the security protocol fails to complete within the Timeout period,= the > function > + shall return EFI_TIMEOUT. > + > + If the security protocol command completes without an error, the func= tion > shall > + return EFI_SUCCESS. If the security protocol command completes with a= n > error, the > + function shall return EFI_DEVICE_ERROR. > + > + @param This Indicates a pointer to the calli= ng context. > + @param MediaId ID of the medium to receive data= from. > + @param Timeout The timeout, in 100ns units, to = use for the > execution > + of the security protocol command= . A Timeout value of 0 > + means that this function will wa= it indefinitely for the > + security protocol command to exe= cute. If Timeout is > greater > + than zero, then this function wi= ll return EFI_TIMEOUT if > the > + time required to execute the rec= eive data command is > greater than Timeout. > + @param SecurityProtocolId The value of the "Security Proto= col" > parameter of > + the security protocol command to= be sent. > + @param SecurityProtocolSpecificData The value of the "Security Proto= col > Specific" parameter > + of the security protocol command= to be sent. > + @param PayloadBufferSize Size in bytes of the payload dat= a buffer. > + @param PayloadBuffer A pointer to a destination buffe= r to store > the security > + protocol command specific payloa= d data for the security > + protocol command. The caller is = responsible for having > + either implicit or explicit owne= rship of the buffer. > + @param PayloadTransferSize A pointer to a buffer to store t= he size in > bytes of the > + data written to the payload data= buffer. > + > + @retval EFI_SUCCESS The security protocol command co= mpleted > successfully. > + @retval EFI_WARN_BUFFER_TOO_SMALL The PayloadBufferSize was too > small to store the available > + data from the device. The Payloa= dBuffer contains the > truncated data. > + @retval EFI_UNSUPPORTED The given MediaId does not suppo= rt > security protocol commands. > + @retval EFI_DEVICE_ERROR The security protocol command > completed with an error. > + @retval EFI_NO_MEDIA There is no media in the device. > + @retval EFI_MEDIA_CHANGED The MediaId is not for the curre= nt > media. > + @retval EFI_INVALID_PARAMETER The PayloadBuffer or > PayloadTransferSize is NULL and > + PayloadBufferSize is non-zero. > + @retval EFI_TIMEOUT A timeout occurred while waiting= for the > security > + protocol command to execute. > + > +**/ > +EFI_STATUS > +EFIAPI > +ScsiDiskReceiveData ( > + IN EFI_STORAGE_SECURITY_COMMAND_PROTOCOL *This, > + IN UINT32 MediaId OPTIONAL, > + IN UINT64 Timeout, > + IN UINT8 SecurityProtocolId, > + IN UINT16 SecurityProtocolSpecificD= ata, > + IN UINTN PayloadBufferSize, > + OUT VOID *PayloadBuffer, > + OUT UINTN *PayloadTransferSize > + ); > + > +/** > + Send a security protocol command to a device. > + > + The SendData function sends a security protocol command containing th= e > payload > + PayloadBuffer to the given MediaId. The security protocol command sen= t > is > + defined by SecurityProtocolId and contains the security protocol spec= ific > data > + SecurityProtocolSpecificData. If the underlying protocol command requ= ires > a > + specific padding for the command payload, the SendData function shall > add padding > + bytes to the command payload to satisfy the padding requirements. > + > + For devices supporting the SCSI command set, the security protocol > command is sent > + using the SECURITY PROTOCOL OUT command defined in SPC-4. > + > + If PayloadBuffer is NULL and PayloadBufferSize is non-zero, the funct= ion > shall > + return EFI_INVALID_PARAMETER. > + > + If the given MediaId does not support security protocol commands, the > function > + shall return EFI_UNSUPPORTED. If there is no media in the device, the > function > + returns EFI_NO_MEDIA. If the MediaId is not the ID for the current me= dia > in the > + device, the function returns EFI_MEDIA_CHANGED. > + > + If the security protocol fails to complete within the Timeout period,= the > function > + shall return EFI_TIMEOUT. > + > + If the security protocol command completes without an error, the func= tion > shall return > + EFI_SUCCESS. If the security protocol command completes with an error= , > the function > + shall return EFI_DEVICE_ERROR. > + > + @param This Indicates a pointer to the calli= ng context. > + @param MediaId ID of the medium to receive data= from. > + @param Timeout The timeout, in 100ns units, to = use for the > execution > + of the security protocol command= . A Timeout value of 0 > + means that this function will wa= it indefinitely for the > + security protocol command to exe= cute. If Timeout is > greater > + than zero, then this function wi= ll return EFI_TIMEOUT if > the > + time required to execute the rec= eive data command is > greater than Timeout. > + @param SecurityProtocolId The value of the "Security Proto= col" > parameter of > + the security protocol command to= be sent. > + @param SecurityProtocolSpecificData The value of the "Security Proto= col > Specific" parameter > + of the security protocol command= to be sent. > + @param PayloadBufferSize Size in bytes of the payload dat= a buffer. > + @param PayloadBuffer A pointer to a destination buffe= r to store > the security > + protocol command specific payloa= d data for the security > + protocol command. > + > + @retval EFI_SUCCESS The security protocol command co= mpleted > successfully. > + @retval EFI_UNSUPPORTED The given MediaId does not suppo= rt > security protocol commands. > + @retval EFI_DEVICE_ERROR The security protocol command > completed with an error. > + @retval EFI_NO_MEDIA There is no media in the device. > + @retval EFI_MEDIA_CHANGED The MediaId is not for the curre= nt > media. > + @retval EFI_INVALID_PARAMETER The PayloadBuffer is NULL and > PayloadBufferSize is non-zero. > + @retval EFI_TIMEOUT A timeout occurred while waiting= for the > security > + protocol command to execute. > + > +**/ > +EFI_STATUS > +EFIAPI > +ScsiDiskSendData ( > + IN EFI_STORAGE_SECURITY_COMMAND_PROTOCOL *This, > + IN UINT32 MediaId OPTIONAL, > + IN UINT64 Timeout, > + IN UINT8 SecurityProtocolId, > + IN UINT16 SecurityProtocolSpecificD= ata, > + IN UINTN PayloadBufferSize, > + OUT VOID *PayloadBuffer > + ); > + > + > /** > Provides inquiry information for the controller type. >=20 > @@ -1428,4 +1581,20 @@ DetermineInstallEraseBlock ( > IN EFI_HANDLE ChildHandle > ); >=20 > +/** > + Determine if EFI Storage Security Command Protocol should be produced= . > + > + @param ScsiDiskDevice The pointer of SCSI_DISK_DEV. > + @param ChildHandle Handle of device. > + > + @retval TRUE Should produce EFI Storage Security Command Protocol= . > + @retval FALSE Should not produce EFI Storage Security Command > Protocol. > + > +**/ > +BOOLEAN > +DetermineInstallStorageSecurity ( > + IN SCSI_DISK_DEV *ScsiDiskDevice, > + IN EFI_HANDLE ChildHandle > + ); > + > #endif > diff --git a/MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBus.c > b/MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBus.c > index c4069aec0f..1caffd38cd 100644 > --- a/MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBus.c > +++ b/MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBus.c > @@ -2,7 +2,7 @@ > SCSI Bus driver that layers on every SCSI Pass Thru and > Extended SCSI Pass Thru protocol in the system. >=20 > -Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.
> +Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved.
> SPDX-License-Identifier: BSD-2-Clause-Patent >=20 > **/ > @@ -1368,7 +1368,8 @@ DiscoverScsiDevice ( > goto Done; > } >=20 > - if (0x1e >=3D InquiryData->Peripheral_Type && InquiryData- > >Peripheral_Type >=3D 0xa) { > + if ((InquiryData->Peripheral_Type >=3D EFI_SCSI_TYPE_RESERVED_LOW) && > + (InquiryData->Peripheral_Type <=3D EFI_SCSI_TYPE_RESERVED_HIGH)) = { > ScsiDeviceFound =3D FALSE; > goto Done; > } > diff --git a/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.c > b/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.c > index fbdf927a11..01d5ad4969 100644 > --- a/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.c > +++ b/MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDisk.c > @@ -1,7 +1,7 @@ > /** @file > SCSI disk driver that layers on every SCSI IO protocol in the system. >=20 > -Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.
> +Copyright (c) 2006 - 2019, Intel Corporation. All rights reserved.
> SPDX-License-Identifier: BSD-2-Clause-Patent >=20 > **/ > @@ -151,7 +151,9 @@ ScsiDiskDriverBindingSupported ( >=20 > Status =3D ScsiIo->GetDeviceType (ScsiIo, &DeviceType); > if (!EFI_ERROR (Status)) { > - if ((DeviceType =3D=3D EFI_SCSI_TYPE_DISK) || (DeviceType =3D=3D > EFI_SCSI_TYPE_CDROM)) { > + if ((DeviceType =3D=3D EFI_SCSI_TYPE_DISK) || > + (DeviceType =3D=3D EFI_SCSI_TYPE_CDROM) || > + (DeviceType =3D=3D EFI_SCSI_TYPE_WLUN)) { > Status =3D EFI_SUCCESS; > } else { > Status =3D EFI_UNSUPPORTED; > @@ -238,6 +240,8 @@ ScsiDiskDriverBindingStart ( > ScsiDiskDevice->BlkIo2.ReadBlocksEx =3D ScsiDiskReadBlo= cksEx; > ScsiDiskDevice->BlkIo2.WriteBlocksEx =3D ScsiDiskWriteBl= ocksEx; > ScsiDiskDevice->BlkIo2.FlushBlocksEx =3D ScsiDiskFlushBl= ocksEx; > + ScsiDiskDevice->StorageSecurity.ReceiveData =3D ScsiDiskReceive= Data; > + ScsiDiskDevice->StorageSecurity.SendData =3D ScsiDiskSendDat= a; > ScsiDiskDevice->EraseBlock.Revision =3D > EFI_ERASE_BLOCK_PROTOCOL_REVISION; > ScsiDiskDevice->EraseBlock.EraseLengthGranularity =3D 1; > ScsiDiskDevice->EraseBlock.EraseBlocks =3D ScsiDiskEraseBl= ocks; > @@ -258,6 +262,10 @@ ScsiDiskDriverBindingStart ( > ScsiDiskDevice->BlkIo.Media->ReadOnly =3D TRUE; > MustReadCapacity =3D FALSE; > break; > + > + case EFI_SCSI_TYPE_WLUN: > + MustReadCapacity =3D FALSE; > + break; > } > // > // The Sense Data Array's initial size is 6 > @@ -309,8 +317,8 @@ ScsiDiskDriverBindingStart ( > // Determine if Block IO & Block IO2 should be produced on this con= troller > // handle > // > - if (DetermineInstallBlockIo(Controller)) { > - InitializeInstallDiskInfo(ScsiDiskDevice, Controller); > + if (DetermineInstallBlockIo (Controller)) { > + InitializeInstallDiskInfo (ScsiDiskDevice, Controller); > Status =3D gBS->InstallMultipleProtocolInterfaces ( > &Controller, > &gEfiBlockIoProtocolGuid, > @@ -321,16 +329,27 @@ ScsiDiskDriverBindingStart ( > &ScsiDiskDevice->DiskInfo, > NULL > ); > - if (!EFI_ERROR(Status)) { > - if (DetermineInstallEraseBlock(ScsiDiskDevice, Controller)) { > + if (!EFI_ERROR (Status)) { > + if (DetermineInstallEraseBlock (ScsiDiskDevice, Controller)) { > Status =3D gBS->InstallProtocolInterface ( > &Controller, > &gEfiEraseBlockProtocolGuid, > EFI_NATIVE_INTERFACE, > &ScsiDiskDevice->EraseBlock > ); > - if (EFI_ERROR(Status)) { > - DEBUG ((EFI_D_ERROR, "ScsiDisk: Failed to install the Erase= Block > Protocol! Status =3D %r\n", Status)); > + if (EFI_ERROR (Status)) { > + DEBUG ((DEBUG_ERROR, "ScsiDisk: Failed to install the Erase= Block > Protocol! Status =3D %r\n", Status)); > + } > + } > + if (DetermineInstallStorageSecurity (ScsiDiskDevice, Controller= )) { > + Status =3D gBS->InstallProtocolInterface ( > + &Controller, > + &gEfiStorageSecurityCommandProtocolGuid, > + EFI_NATIVE_INTERFACE, > + &ScsiDiskDevice->StorageSecurity > + ); > + if (EFI_ERROR (Status)) { > + DEBUG ((DEBUG_ERROR, "ScsiDisk: Failed to install the Stora= ge > Security Command Protocol! Status =3D %r\n", Status)); > } > } > ScsiDiskDevice->ControllerNameTable =3D NULL; > @@ -606,6 +625,11 @@ ScsiDiskReadBlocks ( > // > BlockSize =3D Media->BlockSize; >=20 > + if (BlockSize =3D=3D 0) { > + Status =3D EFI_UNSUPPORTED; > + goto Done; > + } > + > NumberOfBlocks =3D BufferSize / BlockSize; >=20 > if (!(Media->MediaPresent)) { > @@ -742,6 +766,11 @@ ScsiDiskWriteBlocks ( > // > BlockSize =3D Media->BlockSize; >=20 > + if (BlockSize =3D=3D 0) { > + Status =3D EFI_UNSUPPORTED; > + goto Done; > + } > + > NumberOfBlocks =3D BufferSize / BlockSize; >=20 > if (!(Media->MediaPresent)) { > @@ -968,6 +997,11 @@ ScsiDiskReadBlocksEx ( > // > BlockSize =3D Media->BlockSize; >=20 > + if (BlockSize =3D=3D 0) { > + Status =3D EFI_UNSUPPORTED; > + goto Done; > + } > + > NumberOfBlocks =3D BufferSize / BlockSize; >=20 > if (!(Media->MediaPresent)) { > @@ -1131,6 +1165,11 @@ ScsiDiskWriteBlocksEx ( > // > BlockSize =3D Media->BlockSize; >=20 > + if (BlockSize =3D=3D 0) { > + Status =3D EFI_UNSUPPORTED; > + goto Done; > + } > + > NumberOfBlocks =3D BufferSize / BlockSize; >=20 > if (!(Media->MediaPresent)) { > @@ -1708,6 +1747,393 @@ Done: > return Status; > } >=20 > +/** > + Send a security protocol command to a device that receives data and/o= r > the result > + of one or more commands sent by SendData. > + > + The ReceiveData function sends a security protocol command to the giv= en > MediaId. > + The security protocol command sent is defined by SecurityProtocolId a= nd > contains > + the security protocol specific data SecurityProtocolSpecificData. The > function > + returns the data from the security protocol command in PayloadBuffer. > + > + For devices supporting the SCSI command set, the security protocol > command is sent > + using the SECURITY PROTOCOL IN command defined in SPC-4. > + > + If PayloadBufferSize is too small to store the available data from th= e > security > + protocol command, the function shall copy PayloadBufferSize bytes int= o > the > + PayloadBuffer and return EFI_WARN_BUFFER_TOO_SMALL. > + > + If PayloadBuffer or PayloadTransferSize is NULL and PayloadBufferSize= is > non-zero, > + the function shall return EFI_INVALID_PARAMETER. > + > + If the given MediaId does not support security protocol commands, the > function shall > + return EFI_UNSUPPORTED. If there is no media in the device, the funct= ion > returns > + EFI_NO_MEDIA. If the MediaId is not the ID for the current media in t= he > device, > + the function returns EFI_MEDIA_CHANGED. > + > + If the security protocol fails to complete within the Timeout period,= the > function > + shall return EFI_TIMEOUT. > + > + If the security protocol command completes without an error, the func= tion > shall > + return EFI_SUCCESS. If the security protocol command completes with a= n > error, the > + function shall return EFI_DEVICE_ERROR. > + > + @param This Indicates a pointer to the calli= ng context. > + @param MediaId ID of the medium to receive data= from. > + @param Timeout The timeout, in 100ns units, to = use for the > execution > + of the security protocol command= . A Timeout value of 0 > + means that this function will wa= it indefinitely for the > + security protocol command to exe= cute. If Timeout is > greater > + than zero, then this function wi= ll return EFI_TIMEOUT if > the > + time required to execute the rec= eive data command is > greater than Timeout. > + @param SecurityProtocolId The value of the "Security Proto= col" > parameter of > + the security protocol command to= be sent. > + @param SecurityProtocolSpecificData The value of the "Security Proto= col > Specific" parameter > + of the security protocol command= to be sent. > + @param PayloadBufferSize Size in bytes of the payload dat= a buffer. > + @param PayloadBuffer A pointer to a destination buffe= r to store > the security > + protocol command specific payloa= d data for the security > + protocol command. The caller is = responsible for having > + either implicit or explicit owne= rship of the buffer. > + @param PayloadTransferSize A pointer to a buffer to store t= he size in > bytes of the > + data written to the payload data= buffer. > + > + @retval EFI_SUCCESS The security protocol command co= mpleted > successfully. > + @retval EFI_WARN_BUFFER_TOO_SMALL The PayloadBufferSize was too > small to store the available > + data from the device. The Payloa= dBuffer contains the > truncated data. > + @retval EFI_UNSUPPORTED The given MediaId does not suppo= rt > security protocol commands. > + @retval EFI_DEVICE_ERROR The security protocol command > completed with an error. > + @retval EFI_NO_MEDIA There is no media in the device. > + @retval EFI_MEDIA_CHANGED The MediaId is not for the curre= nt > media. > + @retval EFI_INVALID_PARAMETER The PayloadBuffer or > PayloadTransferSize is NULL and > + PayloadBufferSize is non-zero. > + @retval EFI_TIMEOUT A timeout occurred while waiting= for the > security > + protocol command to execute. > + > +**/ > +EFI_STATUS > +EFIAPI > +ScsiDiskReceiveData ( > + IN EFI_STORAGE_SECURITY_COMMAND_PROTOCOL *This, > + IN UINT32 MediaId OPTIONAL, > + IN UINT64 Timeout, > + IN UINT8 SecurityProtocolId, > + IN UINT16 SecurityProtocolSpecificD= ata, > + IN UINTN PayloadBufferSize, > + OUT VOID *PayloadBuffer, > + OUT UINTN *PayloadTransferSize > + ) > +{ > + SCSI_DISK_DEV *ScsiDiskDevice; > + EFI_BLOCK_IO_MEDIA *Media; > + EFI_STATUS Status; > + BOOLEAN MediaChange; > + EFI_TPL OldTpl; > + UINT8 SenseDataLength; > + UINT8 HostAdapterStatus; > + UINT8 TargetStatus; > + VOID *AlignedBuffer; > + BOOLEAN AlignedBufferAllocated; > + > + AlignedBuffer =3D NULL; > + MediaChange =3D FALSE; > + AlignedBufferAllocated =3D FALSE; > + OldTpl =3D gBS->RaiseTPL (TPL_CALLBACK); > + ScsiDiskDevice =3D SCSI_DISK_DEV_FROM_STORSEC (This); > + Media =3D ScsiDiskDevice->BlkIo.Media; > + > + SenseDataLength =3D (UINT8) (ScsiDiskDevice->SenseDataNumber * sizeof > (EFI_SCSI_SENSE_DATA)); > + > + if (!DetermineInstallStorageSecurity (ScsiDiskDevice, ScsiDiskDevice- > >Handle)) { > + Status =3D EFI_UNSUPPORTED; > + goto Done; > + } I think the above 'if' statement is not needed, and should be placed within the below 'if' statement when handling media change: if (MediaChange) {...} (Similar case to ScsiDiskSendData().) > + > + if (!IS_DEVICE_FIXED (ScsiDiskDevice)) { > + Status =3D ScsiDiskDetectMedia (ScsiDiskDevice, FALSE, &MediaChange= ); > + if (EFI_ERROR (Status)) { > + Status =3D EFI_DEVICE_ERROR; > + goto Done; > + } > + > + if (MediaChange) { > + gBS->ReinstallProtocolInterface ( > + ScsiDiskDevice->Handle, > + &gEfiStorageSecurityCommandProtocolGuid, > + &ScsiDiskDevice->StorageSecurity, > + &ScsiDiskDevice->StorageSecurity > + ); The BlockIO(2) & EraseBlocks (if supported) should be reinstalled as well. (Similar case to ScsiDiskSendData().) > + if (Media->MediaPresent) { > + Status =3D EFI_MEDIA_CHANGED; > + } else { > + Status =3D EFI_NO_MEDIA; > + } > + goto Done; > + } > + } > + > + // > + // Validate Media > + // > + if (!(Media->MediaPresent)) { > + Status =3D EFI_NO_MEDIA; > + goto Done; > + } > + > + if ((MediaId !=3D 0) && (MediaId !=3D Media->MediaId)) { > + Status =3D EFI_MEDIA_CHANGED; > + goto Done; > + } > + > + if (PayloadBufferSize !=3D 0) { > + if ((PayloadBuffer =3D=3D NULL) || (PayloadTransferSize =3D=3D NULL= )) { > + Status =3D EFI_INVALID_PARAMETER; > + goto Done; > + } > + > + if ((ScsiDiskDevice->ScsiIo->IoAlign > 1) && !IS_ALIGNED (PayloadBu= ffer, > ScsiDiskDevice->ScsiIo->IoAlign)) { > + AlignedBuffer =3D AllocateAlignedBuffer (ScsiDiskDevice, > PayloadBufferSize); > + if (AlignedBuffer =3D=3D NULL) { > + Status =3D EFI_OUT_OF_RESOURCES; > + goto Done; > + } > + ZeroMem (AlignedBuffer, PayloadBufferSize); > + AlignedBufferAllocated =3D TRUE; > + } else { > + AlignedBuffer =3D PayloadBuffer; > + } > + } > + > + Status =3D ScsiSecurityProtocolInCommand ( > + ScsiDiskDevice->ScsiIo, > + Timeout, > + ScsiDiskDevice->SenseData, > + &SenseDataLength, > + &HostAdapterStatus, > + &TargetStatus, > + SecurityProtocolId, > + SecurityProtocolSpecificData, > + (UINT32) PayloadBufferSize, > + AlignedBuffer, > + (UINT32 *) PayloadTransferSize > + ); > + if (EFI_ERROR (Status)) { > + goto Done; > + } > + > + if (AlignedBufferAllocated) { > + CopyMem (PayloadBuffer, AlignedBuffer, PayloadBufferSize); > + } > + > + if (PayloadBufferSize < *PayloadTransferSize) { > + Status =3D EFI_WARN_BUFFER_TOO_SMALL; > + goto Done; > + } > + > + Status =3D CheckHostAdapterStatus (HostAdapterStatus); > + if (EFI_ERROR (Status)) { > + goto Done; > + } > + > + Status =3D CheckTargetStatus (TargetStatus); > + if (EFI_ERROR (Status)) { > + goto Done; > + } > + > +Done: > + if (AlignedBufferAllocated) { IMO, the content in 'AlignedBuffer' should be wiped out, since it might contain sensitive information. SSC protocol user can control the data in 'PayloadBuffer' but not in 'AlignedBuffer'. > + FreeAlignedBuffer (AlignedBuffer, PayloadBufferSize); > + } > + gBS->RestoreTPL (OldTpl); > + return Status; > +} > + > +/** > + Send a security protocol command to a device. > + > + The SendData function sends a security protocol command containing th= e > payload > + PayloadBuffer to the given MediaId. The security protocol command sen= t > is > + defined by SecurityProtocolId and contains the security protocol spec= ific > data > + SecurityProtocolSpecificData. If the underlying protocol command requ= ires > a > + specific padding for the command payload, the SendData function shall > add padding > + bytes to the command payload to satisfy the padding requirements. > + > + For devices supporting the SCSI command set, the security protocol > command is sent > + using the SECURITY PROTOCOL OUT command defined in SPC-4. > + > + If PayloadBuffer is NULL and PayloadBufferSize is non-zero, the funct= ion > shall > + return EFI_INVALID_PARAMETER. > + > + If the given MediaId does not support security protocol commands, the > function > + shall return EFI_UNSUPPORTED. If there is no media in the device, the > function > + returns EFI_NO_MEDIA. If the MediaId is not the ID for the current me= dia > in the > + device, the function returns EFI_MEDIA_CHANGED. > + > + If the security protocol fails to complete within the Timeout period,= the > function > + shall return EFI_TIMEOUT. > + > + If the security protocol command completes without an error, the func= tion > shall return > + EFI_SUCCESS. If the security protocol command completes with an error= , > the function > + shall return EFI_DEVICE_ERROR. > + > + @param This Indicates a pointer to the calli= ng context. > + @param MediaId ID of the medium to receive data= from. > + @param Timeout The timeout, in 100ns units, to = use for the > execution > + of the security protocol command= . A Timeout value of 0 > + means that this function will wa= it indefinitely for the > + security protocol command to exe= cute. If Timeout is > greater > + than zero, then this function wi= ll return EFI_TIMEOUT if > the > + time required to execute the rec= eive data command is > greater than Timeout. > + @param SecurityProtocolId The value of the "Security Proto= col" > parameter of > + the security protocol command to= be sent. > + @param SecurityProtocolSpecificData The value of the "Security Proto= col > Specific" parameter > + of the security protocol command= to be sent. > + @param PayloadBufferSize Size in bytes of the payload dat= a buffer. > + @param PayloadBuffer A pointer to a destination buffe= r to store > the security > + protocol command specific payloa= d data for the security > + protocol command. > + > + @retval EFI_SUCCESS The security protocol command co= mpleted > successfully. > + @retval EFI_UNSUPPORTED The given MediaId does not suppo= rt > security protocol commands. > + @retval EFI_DEVICE_ERROR The security protocol command > completed with an error. > + @retval EFI_NO_MEDIA There is no media in the device. > + @retval EFI_MEDIA_CHANGED The MediaId is not for the curre= nt > media. > + @retval EFI_INVALID_PARAMETER The PayloadBuffer is NULL and > PayloadBufferSize is non-zero. > + @retval EFI_TIMEOUT A timeout occurred while waiting= for the > security > + protocol command to execute. > + > +**/ > +EFI_STATUS > +EFIAPI > +ScsiDiskSendData ( > + IN EFI_STORAGE_SECURITY_COMMAND_PROTOCOL *This, > + IN UINT32 MediaId OPTIONAL, > + IN UINT64 Timeout, > + IN UINT8 SecurityProtocolId, > + IN UINT16 SecurityProtocolSpecificD= ata, > + IN UINTN PayloadBufferSize, > + OUT VOID *PayloadBuffer > + ) > +{ > + SCSI_DISK_DEV *ScsiDiskDevice; > + EFI_BLOCK_IO_MEDIA *Media; > + EFI_STATUS Status; > + BOOLEAN MediaChange; > + EFI_TPL OldTpl; > + UINT8 SenseDataLength; > + UINT8 HostAdapterStatus; > + UINT8 TargetStatus; > + VOID *AlignedBuffer; > + BOOLEAN AlignedBufferAllocated; > + > + AlignedBuffer =3D NULL; > + MediaChange =3D FALSE; > + AlignedBufferAllocated =3D FALSE; > + OldTpl =3D gBS->RaiseTPL (TPL_CALLBACK); > + ScsiDiskDevice =3D SCSI_DISK_DEV_FROM_STORSEC (This); > + Media =3D ScsiDiskDevice->BlkIo.Media; > + > + SenseDataLength =3D (UINT8) (ScsiDiskDevice->SenseDataNumber * sizeof > (EFI_SCSI_SENSE_DATA)); > + > + if (!DetermineInstallStorageSecurity (ScsiDiskDevice, ScsiDiskDevice- > >Handle)) { > + Status =3D EFI_UNSUPPORTED; > + goto Done; > + } > + > + if (!IS_DEVICE_FIXED (ScsiDiskDevice)) { > + Status =3D ScsiDiskDetectMedia (ScsiDiskDevice, FALSE, &MediaChange= ); > + if (EFI_ERROR (Status)) { > + Status =3D EFI_DEVICE_ERROR; > + goto Done; > + } > + > + if (MediaChange) { > + gBS->ReinstallProtocolInterface ( > + ScsiDiskDevice->Handle, > + &gEfiStorageSecurityCommandProtocolGuid, > + &ScsiDiskDevice->StorageSecurity, > + &ScsiDiskDevice->StorageSecurity > + ); > + if (Media->MediaPresent) { > + Status =3D EFI_MEDIA_CHANGED; > + } else { > + Status =3D EFI_NO_MEDIA; > + } > + goto Done; > + } > + } > + > + // > + // Validate Media > + // > + if (!(Media->MediaPresent)) { > + Status =3D EFI_NO_MEDIA; > + goto Done; > + } > + > + if ((MediaId !=3D 0) && (MediaId !=3D Media->MediaId)) { > + Status =3D EFI_MEDIA_CHANGED; > + goto Done; > + } > + > + if (Media->ReadOnly) { > + Status =3D EFI_WRITE_PROTECTED; > + goto Done; > + } > + > + if (PayloadBufferSize !=3D 0) { > + if (PayloadBuffer =3D=3D NULL) { > + Status =3D EFI_INVALID_PARAMETER; > + goto Done; > + } > + > + if ((ScsiDiskDevice->ScsiIo->IoAlign > 1) && !IS_ALIGNED (PayloadBu= ffer, > ScsiDiskDevice->ScsiIo->IoAlign)) { > + AlignedBuffer =3D AllocateAlignedBuffer (ScsiDiskDevice, > PayloadBufferSize); > + if (AlignedBuffer =3D=3D NULL) { > + Status =3D EFI_OUT_OF_RESOURCES; > + goto Done; > + } > + CopyMem (AlignedBuffer, PayloadBuffer, PayloadBufferSize); > + AlignedBufferAllocated =3D TRUE; > + } else { > + AlignedBuffer =3D PayloadBuffer; > + } > + } > + > + Status =3D ScsiSecurityProtocolOutCommand ( > + ScsiDiskDevice->ScsiIo, > + Timeout, > + ScsiDiskDevice->SenseData, > + &SenseDataLength, > + &HostAdapterStatus, > + &TargetStatus, > + SecurityProtocolId, > + SecurityProtocolSpecificData, > + (UINT32) PayloadBufferSize, > + AlignedBuffer > + ); > + if (EFI_ERROR (Status)) { > + goto Done; > + } > + > + Status =3D CheckHostAdapterStatus (HostAdapterStatus); > + if (EFI_ERROR (Status)) { > + goto Done; > + } > + > + Status =3D CheckTargetStatus (TargetStatus); > + if (EFI_ERROR (Status)) { > + goto Done; > + } > + > +Done: > + if (AlignedBufferAllocated) { IMO, the content in 'AlignedBuffer' should be wiped out, since it might contain sensitive information. SSC protocol user can control the data in 'PayloadBuffer' but not in 'AlignedBuffer'. > + FreeAlignedBuffer (AlignedBuffer, PayloadBufferSize); > + } > + gBS->RestoreTPL (OldTpl); > + return Status; > +} > + >=20 > /** > Detect Device and read out capacity ,if error occurs, parse the sense= key. > @@ -2261,6 +2687,8 @@ ScsiDiskTestUnitReady ( > return EFI_DEVICE_ERROR; > } >=20 > + ScsiDiskDevice->BlkIo.Media->MediaPresent =3D TRUE; > + > if (SenseDataLength !=3D 0) { > *NumberOfSenseKeys =3D SenseDataLength / sizeof > (EFI_SCSI_SENSE_DATA); > *SenseDataArray =3D ScsiDiskDevice->SenseData; > @@ -2315,13 +2743,12 @@ DetectMediaParsingSenseKeys ( > BOOLEAN RetryLater; >=20 > // > - // Default is to read capacity, unless.. > + // Default is no action > // > - *Action =3D ACTION_READ_CAPACITY; > + *Action =3D ACTION_NO_ACTION; >=20 > if (NumberOfSenseKeys =3D=3D 0) { > if (ScsiDiskDevice->BlkIo.Media->MediaPresent =3D=3D TRUE) { > - *Action =3D ACTION_NO_ACTION; > } I do not think the behavior is the same after the patch. Can it be: if (NumberOfSenseKeys =3D=3D 0) { if (!ScsiDiskDevice->BlkIo.Media->MediaPresent) { *Action =3D ACTION_READ_CAPACITY; } return EFI_SUCCESS; } > return EFI_SUCCESS; > } > @@ -2331,7 +2758,6 @@ DetectMediaParsingSenseKeys ( > // No Sense Key returned from last submitted command > // > if (ScsiDiskDevice->BlkIo.Media->MediaPresent =3D=3D TRUE) { > - *Action =3D ACTION_NO_ACTION; > } I do not think the behavior is the same after the patch. Can it be: if (!ScsiDiskHaveSenseKey (SenseData, NumberOfSenseKeys)) { // // No Sense Key returned from last submitted command // if (!ScsiDiskDevice->BlkIo.Media->MediaPresent) { *Action =3D ACTION_READ_CAPACITY; } return EFI_SUCCESS; } Best Regards, Hao Wu > return EFI_SUCCESS; > } > @@ -2339,13 +2765,13 @@ DetectMediaParsingSenseKeys ( > if (ScsiDiskIsNoMedia (SenseData, NumberOfSenseKeys)) { > ScsiDiskDevice->BlkIo.Media->MediaPresent =3D FALSE; > ScsiDiskDevice->BlkIo.Media->LastBlock =3D 0; > - *Action =3D ACTION_NO_ACTION; > DEBUG ((EFI_D_VERBOSE, "ScsiDisk: ScsiDiskIsNoMedia\n")); > return EFI_SUCCESS; > } >=20 > if (ScsiDiskIsMediaChange (SenseData, NumberOfSenseKeys)) { > ScsiDiskDevice->BlkIo.Media->MediaId++; > + *Action =3D ACTION_READ_CAPACITY; > DEBUG ((EFI_D_VERBOSE, "ScsiDisk: ScsiDiskIsMediaChange!\n")); > return EFI_SUCCESS; > } > @@ -2374,7 +2800,6 @@ DetectMediaParsingSenseKeys ( > DEBUG ((EFI_D_VERBOSE, "ScsiDisk: ScsiDiskDriveNotReady!\n")); > return EFI_SUCCESS; > } > - *Action =3D ACTION_NO_ACTION; > return EFI_DEVICE_ERROR; > } >=20 > @@ -2808,8 +3233,6 @@ GetMediaInfo ( > } > } > } > - > - ScsiDiskDevice->BlkIo.Media->MediaPresent =3D TRUE; > } >=20 > /** > @@ -5358,6 +5781,14 @@ DetermineInstallEraseBlock ( > RetVal =3D TRUE; > CapacityData16 =3D NULL; >=20 > + // > + // UNMAP command is not supported by any of the UFS WLUNs. > + // > + if (ScsiDiskDevice->DeviceType =3D=3D EFI_SCSI_TYPE_WLUN) { > + RetVal =3D FALSE; > + goto Done; > + } > + > Status =3D gBS->HandleProtocol ( > ChildHandle, > &gEfiDevicePathProtocolGuid, > @@ -5460,6 +5891,65 @@ Done: > return RetVal; > } >=20 > +/** > + Determine if EFI Storage Security Command Protocol should be produced= . > + > + @param ScsiDiskDevice The pointer of SCSI_DISK_DEV. > + @param ChildHandle Handle of device. > + > + @retval TRUE Should produce EFI Storage Security Command Protocol= . > + @retval FALSE Should not produce EFI Storage Security Command > Protocol. > + > +**/ > +BOOLEAN > +DetermineInstallStorageSecurity ( > + IN SCSI_DISK_DEV *ScsiDiskDevice, > + IN EFI_HANDLE ChildHandle > + ) > +{ > + EFI_STATUS Status; > + UFS_DEVICE_PATH *UfsDevice; > + BOOLEAN RetVal; > + EFI_DEVICE_PATH_PROTOCOL *DevicePathNode; > + > + UfsDevice =3D NULL; > + RetVal =3D TRUE; > + > + Status =3D gBS->HandleProtocol ( > + ChildHandle, > + &gEfiDevicePathProtocolGuid, > + (VOID **) &DevicePathNode > + ); > + // > + // Device Path protocol must be installed on the device handle. > + // > + ASSERT_EFI_ERROR (Status); > + > + while (!IsDevicePathEndType (DevicePathNode)) { > + // > + // For now, only support Storage Security Command Protocol on UFS > devices. > + // > + if ((DevicePathNode->Type =3D=3D MESSAGING_DEVICE_PATH) && > + (DevicePathNode->SubType =3D=3D MSG_UFS_DP)) { > + UfsDevice =3D (UFS_DEVICE_PATH *) DevicePathNode; > + break; > + } > + > + DevicePathNode =3D NextDevicePathNode (DevicePathNode); > + } > + if (UfsDevice =3D=3D NULL) { > + RetVal =3D FALSE; > + goto Done; > + } > + > + if (UfsDevice->Lun !=3D UFS_WLUN_RPMB) { > + RetVal =3D FALSE; > + } > + > +Done: > + return RetVal; > +} > + > /** > Provides inquiry information for the controller type. >=20 > diff --git a/MdeModulePkg/Bus/Ufs/UfsPassThruDxe/UfsPassThru.c > b/MdeModulePkg/Bus/Ufs/UfsPassThruDxe/UfsPassThru.c > index 1518b251d8..0bb67f2ddc 100644 > --- a/MdeModulePkg/Bus/Ufs/UfsPassThruDxe/UfsPassThru.c > +++ b/MdeModulePkg/Bus/Ufs/UfsPassThruDxe/UfsPassThru.c > @@ -1,6 +1,6 @@ > /** @file >=20 > - Copyright (c) 2014 - 2018, Intel Corporation. All rights reserved. > + Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved. > SPDX-License-Identifier: BSD-2-Clause-Patent >=20 > **/ > @@ -819,7 +819,9 @@ UfsPassThruDriverBindingStart ( > UINTN UfsHcBase; > UINT32 Index; > UFS_UNIT_DESC UnitDescriptor; > + UFS_DEV_DESC DeviceDescriptor; > UINT32 UnitDescriptorSize; > + UINT32 DeviceDescriptorSize; >=20 > Status =3D EFI_SUCCESS; > UfsHc =3D NULL; > @@ -894,7 +896,6 @@ UfsPassThruDriverBindingStart ( >=20 > // > // Check if 8 common luns are active and set corresponding bit mask. > - // TODO: Parse device descriptor to decide if exposing RPMB LUN to up= per > layer for authentication access. > // > UnitDescriptorSize =3D sizeof (UFS_UNIT_DESC); > for (Index =3D 0; Index < 8; Index++) { > @@ -909,6 +910,20 @@ UfsPassThruDriverBindingStart ( > } > } >=20 > + // > + // Check if RPMB WLUN is supported and set corresponding bit mask. > + // > + DeviceDescriptorSize =3D sizeof (UFS_DEV_DESC); > + Status =3D UfsRwDeviceDesc (Private, TRUE, UfsDeviceDesc, 0, 0, > &DeviceDescriptor, &DeviceDescriptorSize); > + if (EFI_ERROR (Status)) { > + DEBUG ((DEBUG_ERROR, "Failed to read device descriptor, status =3D = %r\n", > Status)); > + } else { > + if (DeviceDescriptor.SecurityLun =3D=3D 0x1) { > + DEBUG ((DEBUG_INFO, "UFS WLUN RPMB is supported\n")); > + Private->Luns.BitMask |=3D BIT11; > + } > + } > + > // > // Start the asynchronous interrupt monitor > // > -- > 2.16.2.windows.1 >=20 >=20 >=20