EFI_UNIX_IO_PROTOCOL *UnixIo;\r
UART_DEVICE_PATH *UartNode;\r
\r
+ //\r
+ // Check RemainingDevicePath validation\r
+ //\r
+ if (RemainingDevicePath != NULL) {\r
+ //\r
+ // Check if RemainingDevicePath is the End of Device Path Node, \r
+ // if yes, go on checking other conditions\r
+ //\r
+ if (!IsDevicePathEnd (RemainingDevicePath)) {\r
+ //\r
+ // If RemainingDevicePath isn't the End of Device Path Node,\r
+ // check its validation\r
+ //\r
+ Status = EFI_UNSUPPORTED;\r
+ UartNode = (UART_DEVICE_PATH *) RemainingDevicePath;\r
+ if (UartNode->Header.Type != MESSAGING_DEVICE_PATH ||\r
+ UartNode->Header.SubType != MSG_UART_DP ||\r
+ DevicePathNodeLength((EFI_DEVICE_PATH_PROTOCOL *)UartNode) != sizeof(UART_DEVICE_PATH)) {\r
+ goto Error;\r
+ }\r
+ if (UartNode->BaudRate < 0 || UartNode->BaudRate > SERIAL_PORT_MAX_BAUD_RATE) {\r
+ goto Error;\r
+ }\r
+ if (UartNode->Parity < NoParity || UartNode->Parity > SpaceParity) {\r
+ goto Error;\r
+ }\r
+ if (UartNode->DataBits < 5 || UartNode->DataBits > 8) {\r
+ goto Error;\r
+ }\r
+ if (UartNode->StopBits < OneStopBit || UartNode->StopBits > TwoStopBits) {\r
+ goto Error;\r
+ }\r
+ if ((UartNode->DataBits == 5) && (UartNode->StopBits == TwoStopBits)) {\r
+ goto Error;\r
+ }\r
+ if ((UartNode->DataBits >= 6) && (UartNode->DataBits <= 8) && (UartNode->StopBits == OneFiveStopBits)) {\r
+ goto Error;\r
+ }\r
+ }\r
+ }\r
+\r
//\r
// Open the IO Abstraction(s) needed to perform the supported test\r
//\r
Status = gBS->OpenProtocol (\r
Handle,\r
- &gEfiDevicePathProtocolGuid,\r
- (VOID**)&ParentDevicePath,\r
+ &gEfiUnixIoProtocolGuid,\r
+ (VOID**)&UnixIo,\r
This->DriverBindingHandle,\r
Handle,\r
EFI_OPEN_PROTOCOL_BY_DRIVER\r
return Status;\r
}\r
\r
+ //\r
+ // Close the I/O Abstraction(s) used to perform the supported test\r
+ //\r
gBS->CloseProtocol (\r
Handle,\r
- &gEfiDevicePathProtocolGuid,\r
+ &gEfiUnixIoProtocolGuid,\r
This->DriverBindingHandle,\r
Handle\r
);\r
\r
+ //\r
+ // Open the EFI Device Path protocol needed to perform the supported test\r
+ //\r
Status = gBS->OpenProtocol (\r
Handle,\r
- &gEfiUnixIoProtocolGuid,\r
- (VOID**)&UnixIo,\r
+ &gEfiDevicePathProtocolGuid,\r
+ (VOID**)&ParentDevicePath,\r
This->DriverBindingHandle,\r
Handle,\r
EFI_OPEN_PROTOCOL_BY_DRIVER\r
return Status;\r
}\r
\r
+ //\r
+ // Close protocol, don't use device path protocol in the Support() function\r
+ //\r
+ gBS->CloseProtocol (\r
+ Handle,\r
+ &gEfiDevicePathProtocolGuid,\r
+ This->DriverBindingHandle,\r
+ Handle\r
+ );\r
+\r
//\r
// Make sure that the Unix Thunk Protocol is valid\r
//\r
goto Error;\r
}\r
\r
- if (RemainingDevicePath != NULL) {\r
- Status = EFI_UNSUPPORTED;\r
- UartNode = (UART_DEVICE_PATH *) RemainingDevicePath;\r
- if (UartNode->Header.Type != MESSAGING_DEVICE_PATH ||\r
- UartNode->Header.SubType != MSG_UART_DP ||\r
- DevicePathNodeLength((EFI_DEVICE_PATH_PROTOCOL *)UartNode) != sizeof(UART_DEVICE_PATH)) {\r
- goto Error;\r
- }\r
- if (UartNode->BaudRate < 0 || UartNode->BaudRate > SERIAL_PORT_MAX_BAUD_RATE) {\r
- goto Error;\r
- }\r
- if (UartNode->Parity < NoParity || UartNode->Parity > SpaceParity) {\r
- goto Error;\r
- }\r
- if (UartNode->DataBits < 5 || UartNode->DataBits > 8) {\r
- goto Error;\r
- }\r
- if (UartNode->StopBits < OneStopBit || UartNode->StopBits > TwoStopBits) {\r
- goto Error;\r
- }\r
- if ((UartNode->DataBits == 5) && (UartNode->StopBits == TwoStopBits)) {\r
- goto Error;\r
- }\r
- if ((UartNode->DataBits >= 6) && (UartNode->DataBits <= 8) && (UartNode->StopBits == OneFiveStopBits)) {\r
- goto Error;\r
- }\r
- Status = EFI_SUCCESS;\r
- }\r
+ return EFI_SUCCESS;\r
\r
Error:\r
- //\r
- // Close the I/O Abstraction(s) used to perform the supported test\r
- //\r
- gBS->CloseProtocol (\r
- Handle,\r
- &gEfiUnixIoProtocolGuid,\r
- This->DriverBindingHandle,\r
- Handle\r
- );\r
-\r
return Status;\r
}\r
\r
UINTN Index;\r
EFI_SERIAL_IO_PROTOCOL *SerialIo;\r
CHAR8 AsciiDevName[1024];\r
+ UART_DEVICE_PATH *UartNode;\r
\r
DEBUG ((EFI_D_INFO, "SerialIo drive binding start!\r\n"));\r
Private = NULL;\r
\r
if (Status == EFI_ALREADY_STARTED) {\r
\r
- if (RemainingDevicePath == NULL) {\r
+ if (RemainingDevicePath == NULL || IsDevicePathEnd (RemainingDevicePath)) {\r
+ //\r
+ // If RemainingDevicePath is NULL or is the End of Device Path Node\r
+ //\r
return EFI_SUCCESS;\r
}\r
\r
EFI_OPEN_PROTOCOL_GET_PROTOCOL\r
);\r
if (!EFI_ERROR (Status)) {\r
- CopyMem (&Node, RemainingDevicePath, sizeof (UART_DEVICE_PATH));\r
+ UartNode = (UART_DEVICE_PATH *) RemainingDevicePath;\r
Status = SerialIo->SetAttributes (\r
SerialIo,\r
- Node.BaudRate,\r
+ UartNode->BaudRate,\r
SerialIo->Mode->ReceiveFifoDepth,\r
SerialIo->Mode->Timeout,\r
- Node.Parity,\r
- Node.DataBits,\r
- Node.StopBits\r
+ UartNode->Parity,\r
+ UartNode->DataBits,\r
+ UartNode->StopBits\r
);\r
}\r
break;\r
}\r
\r
FreePool (OpenInfoBuffer);\r
- return Status;\r
+ if (Index < EntryCount) {\r
+ //\r
+ // If gEfiUnixIoProtocolGuid is opened by one child device, return\r
+ //\r
+ return Status;\r
+ }\r
+ //\r
+ // If gEfiUnixIoProtocolGuid is not opened by any child device,\r
+ // go further to create child device handle based on RemainingDevicePath\r
+ //\r
+ }\r
+\r
+ if (RemainingDevicePath == NULL) {\r
+ //\r
+ // Build the device path by appending the UART node to the ParentDevicePath\r
+ // from the UnixIo handle. The Uart setings are zero here, since\r
+ // SetAttribute() will update them to match the default setings.\r
+ //\r
+ ZeroMem (&Node, sizeof (UART_DEVICE_PATH));\r
+ Node.Header.Type = MESSAGING_DEVICE_PATH;\r
+ Node.Header.SubType = MSG_UART_DP;\r
+ SetDevicePathNodeLength ((EFI_DEVICE_PATH_PROTOCOL *) &Node, sizeof (UART_DEVICE_PATH));\r
+\r
+ } else if (!IsDevicePathEnd (RemainingDevicePath)) {\r
+ //\r
+ // If RemainingDevicePath isn't the End of Device Path Node, \r
+ // only scan the specified device by RemainingDevicePath\r
+ //\r
+ //\r
+ // Match the configuration of the RemainingDevicePath. IsHandleSupported()\r
+ // already checked to make sure the RemainingDevicePath contains settings\r
+ // that we can support.\r
+ //\r
+ CopyMem (&Node, RemainingDevicePath, sizeof (UART_DEVICE_PATH));\r
+\r
+ } else {\r
+ //\r
+ // If RemainingDevicePath is the End of Device Path Node,\r
+ // skip enumerate any device and return EFI_SUCESSS\r
+ // \r
+ return EFI_SUCCESS;\r
}\r
\r
//\r
Private->Fifo.Last = 0;\r
Private->Fifo.Surplus = SERIAL_MAX_BUFFER_SIZE;\r
\r
+ CopyMem (&Private->UartDevicePath, &Node, sizeof (UART_DEVICE_PATH));\r
+\r
AddUnicodeString (\r
"eng",\r
gUnixSerialIoComponentName.SupportedLanguages,\r
Private->SerialIo.Read = UnixSerialIoRead;\r
Private->SerialIo.Mode = &Private->SerialIoMode;\r
\r
- if (RemainingDevicePath != NULL) {\r
- //\r
- // Match the configuration of the RemainingDevicePath. IsHandleSupported()\r
- // already checked to make sure the RemainingDevicePath contains settings\r
- // that we can support.\r
- //\r
- CopyMem (&Private->UartDevicePath, RemainingDevicePath, sizeof (UART_DEVICE_PATH));\r
- } else {\r
- //\r
- // Build the device path by appending the UART node to the ParentDevicePath\r
- // from the UnixIo handle. The Uart setings are zero here, since\r
- // SetAttribute() will update them to match the default setings.\r
- //\r
- ZeroMem (&Private->UartDevicePath, sizeof (UART_DEVICE_PATH));\r
- Private->UartDevicePath.Header.Type = MESSAGING_DEVICE_PATH;\r
- Private->UartDevicePath.Header.SubType = MSG_UART_DP;\r
- SetDevicePathNodeLength ((EFI_DEVICE_PATH_PROTOCOL *) &Private->UartDevicePath, sizeof (UART_DEVICE_PATH));\r
- }\r
+\r
\r
//\r
// Build the device path by appending the UART node to the ParentDevicePath\r