Пример #1
0
/**
  Write the specified number of bytes to serial device.

  @param[in]      This       Pointer to EFI_SERIAL_IO_PROTOCOL.
  @param[in, out] BufferSize On input the size of Buffer, on output the amount of
                             data actually written.
  @param[in]      Buffer     The buffer of data to write.

  @retval EFI_SUCCESS        The data were written successfully.
  @retval EFI_DEVICE_ERROR   The device reported an error.
  @retval EFI_TIMEOUT        The write operation was stopped due to timeout.

**/
EFI_STATUS
EFIAPI
SerialWrite (
  IN EFI_SERIAL_IO_PROTOCOL  *This,
  IN OUT UINTN               *BufferSize,
  IN VOID                    *Buffer
  )
{
  DEBUG_PORT_HANDLE                Handle;

  Handle = GetDebugPortHandle ();
  
  if ((mSerialIoMode.ControlMask & EFI_SERIAL_SOFTWARE_LOOPBACK_ENABLE) != 0)  {
    if (*BufferSize == 0) {
      return EFI_SUCCESS;
    }
    if ((mLoopbackBuffer & SERIAL_PORT_LOOPBACK_BUFFER_FULL) != 0) {
      *BufferSize = 0;
      return EFI_TIMEOUT;
    }
    mLoopbackBuffer = SERIAL_PORT_LOOPBACK_BUFFER_FULL | *(UINT8 *)Buffer;
    *BufferSize = 1;
  } else {
    *BufferSize = DebugPortWriteBuffer (Handle, Buffer, *BufferSize);
  }
  return EFI_SUCCESS;
}
Пример #2
0
/**
  Get ControlBits.

  @param[in]  This         Pointer to EFI_SERIAL_IO_PROTOCOL.
  @param[out] Control      Control signals of the serial device.

  @retval EFI_SUCCESS  Get Control signals successfully.

**/
EFI_STATUS
EFIAPI
SerialGetControl (
  IN EFI_SERIAL_IO_PROTOCOL  *This,
  OUT UINT32                 *Control
  )
{
  DEBUG_PORT_HANDLE                Handle;

  Handle = GetDebugPortHandle ();
  
  //
  // Always assume the output buffer is empty and the Debug Communication Library can process
  // more write requests.
  //
  *Control = mSerialIoMode.ControlMask | EFI_SERIAL_OUTPUT_BUFFER_EMPTY;
  
  //
  // Check to see if the Terminal FIFO is empty and 
  // check to see if the input buffer in the Debug Communication Library is empty
  //
  if (!IsDebugTermianlFifoEmpty (&mSerialFifoForTerminal) || DebugPortPollBuffer (Handle)) {
    *Control &= ~EFI_SERIAL_INPUT_BUFFER_EMPTY;
  }
  return EFI_SUCCESS;
}
Пример #3
0
/**
  Write the specified number of bytes to serial device.

  @param[in]      This       Pointer to EFI_SERIAL_IO_PROTOCOL.
  @param[in, out] BufferSize On input the size of Buffer, on output the amount of
                             data actually written.
  @param[in]      Buffer     The buffer of data to write.

  @retval EFI_SUCCESS        The data were written successfully.
  @retval EFI_DEVICE_ERROR   The device reported an error.
  @retval EFI_TIMEOUT        The write operation was stopped due to timeout.

**/
EFI_STATUS
EFIAPI
SerialWrite (
  IN EFI_SERIAL_IO_PROTOCOL  *This,
  IN OUT UINTN               *BufferSize,
  IN VOID                    *Buffer
  )
{
  DEBUG_PORT_HANDLE                Handle;
  BOOLEAN                          DebugTimerInterruptState;
  EFI_TPL                          Tpl;

  //
  // Raise TPL to prevent recursion from EFI timer interrupts
  //
  Tpl = gBS->RaiseTPL (TPL_NOTIFY);

  //
  // Save and disable Debug Timer interrupt to avoid it to access Debug Port
  //
  DebugTimerInterruptState = SaveAndSetDebugTimerInterrupt (FALSE);
  Handle = GetDebugPortHandle ();

  if ((mSerialIoMode.ControlMask & EFI_SERIAL_SOFTWARE_LOOPBACK_ENABLE) != 0)  {
    if (*BufferSize == 0) {
      return EFI_SUCCESS;
    }
    if ((mLoopbackBuffer & SERIAL_PORT_LOOPBACK_BUFFER_FULL) != 0) {
      *BufferSize = 0;
      return EFI_TIMEOUT;
    }
    mLoopbackBuffer = SERIAL_PORT_LOOPBACK_BUFFER_FULL | *(UINT8 *)Buffer;
    *BufferSize = 1;
  } else {
    *BufferSize = DebugPortWriteBuffer (Handle, Buffer, *BufferSize);
  }

  //
  // Restore Debug Timer interrupt
  //
  SaveAndSetDebugTimerInterrupt (DebugTimerInterruptState);

  //
  // Restore to original TPL
  //
  gBS->RestoreTPL (Tpl);

  return EFI_SUCCESS;
}
Пример #4
0
/**
  Get ControlBits.

  @param[in]  This         Pointer to EFI_SERIAL_IO_PROTOCOL.
  @param[out] Control      Control signals of the serial device.

  @retval EFI_SUCCESS  Get Control signals successfully.

**/
EFI_STATUS
EFIAPI
SerialGetControl (
  IN EFI_SERIAL_IO_PROTOCOL  *This,
  OUT UINT32                 *Control
  )
{
  DEBUG_PORT_HANDLE                Handle;
  BOOLEAN                          DebugTimerInterruptState;
  EFI_TPL                          Tpl;

  //
  // Raise TPL to prevent recursion from EFI timer interrupts
  //
  Tpl = gBS->RaiseTPL (TPL_NOTIFY);

  //
  // Save and disable Debug Timer interrupt to avoid it to access Debug Port
  //
  DebugTimerInterruptState = SaveAndSetDebugTimerInterrupt (FALSE);
  Handle = GetDebugPortHandle ();

  //
  // Always assume the output buffer is empty and the Debug Communication Library can process
  // more write requests.
  //
  *Control = mSerialIoMode.ControlMask | EFI_SERIAL_OUTPUT_BUFFER_EMPTY;

  //
  // Check to see if the Terminal FIFO is empty and
  // check to see if the input buffer in the Debug Communication Library is empty
  //
  if (!IsDebugTermianlFifoEmpty (&mSerialFifoForTerminal) || DebugPortPollBuffer (Handle)) {
    *Control &= ~EFI_SERIAL_INPUT_BUFFER_EMPTY;
  }

  //
  // Restore Debug Timer interrupt
  //
  SaveAndSetDebugTimerInterrupt (DebugTimerInterruptState);

  //
  // Restore to original TPL
  //
  gBS->RestoreTPL (Tpl);

  return EFI_SUCCESS;
}
Пример #5
0
/**
  Read the specified number of bytes from serial device.

  @param[in] This            Pointer to EFI_SERIAL_IO_PROTOCOL.
  @param[in, out] BufferSize On input the size of Buffer, on output the amount of
                             data returned in buffer.
  @param[out] Buffer         The buffer to return the data into.

  @retval EFI_SUCCESS        The data were read successfully.
  @retval EFI_DEVICE_ERROR   The device reported an error.
  @retval EFI_TIMEOUT        The read operation was stopped due to timeout.

**/
EFI_STATUS
EFIAPI
SerialRead (
  IN EFI_SERIAL_IO_PROTOCOL  *This,
  IN OUT UINTN               *BufferSize,
  OUT VOID                   *Buffer
  )
{
  EFI_STATUS                  Status;
  UINTN                       Index;
  UINT8                       *Uint8Buffer;
  BOOLEAN                     DebugTimerInterruptState;
  EFI_TPL                     Tpl;
  DEBUG_PORT_HANDLE           Handle;
  DEBUG_PACKET_HEADER         DebugHeader;
  UINT8                       *Data8;

  //
  // Raise TPL to prevent recursion from EFI timer interrupts
  //
  Tpl = gBS->RaiseTPL (TPL_NOTIFY);

  //
  // Save and disable Debug Timer interrupt to avoid it to access Debug Port
  //
  DebugTimerInterruptState = SaveAndSetDebugTimerInterrupt (FALSE);
  Handle = GetDebugPortHandle ();

  Data8 = (UINT8 *) &DebugHeader;
  Uint8Buffer = (UINT8 *)Buffer;
  if ((mSerialIoMode.ControlMask & EFI_SERIAL_SOFTWARE_LOOPBACK_ENABLE) != 0)  {
    if ((mLoopbackBuffer & SERIAL_PORT_LOOPBACK_BUFFER_FULL) == 0) {
      return EFI_TIMEOUT;
    }
    *Uint8Buffer = (UINT8)(mLoopbackBuffer & 0xff);
    mLoopbackBuffer = 0;
    *BufferSize = 1;
  } else {
    for (Index = 0; Index < *BufferSize; Index++) {
      //
      // Read input character from terminal FIFO firstly
      //
      Status = DebugTerminalFifoRemove (&mSerialFifoForTerminal, Data8);
      if (Status == EFI_SUCCESS) {
        *Uint8Buffer = *Data8;
        Uint8Buffer ++;
        continue;
      }
      //
      // Read the input character from Debug Port
      //
      if (!DebugPortPollBuffer (Handle)) {
        break;
      }
      DebugPortReadBuffer (Handle, Data8, 1, 0);

      if (*Data8 == DEBUG_STARTING_SYMBOL_ATTACH) {
        //
        // Add the debug symbol into Debug FIFO
        //
        DebugAgentMsgPrint (DEBUG_AGENT_INFO, "Terminal Timer attach symbol received %x", *Data8);
        DebugTerminalFifoAdd (&mSerialFifoForDebug, *Data8);
      } else if (*Data8 == DEBUG_STARTING_SYMBOL_NORMAL) {
        Status = ReadRemainingBreakPacket (Handle, &DebugHeader);
        if (Status == EFI_SUCCESS) {
          DebugAgentMsgPrint (DEBUG_AGENT_INFO, "Terminal Timer break symbol received %x", DebugHeader.Command);
          DebugTerminalFifoAdd (&mSerialFifoForDebug, DebugHeader.Command);
        }
        if (Status == EFI_TIMEOUT) {
          continue;
        }
      } else {
        *Uint8Buffer = *Data8;
        Uint8Buffer ++;
      }
    }
    *BufferSize = (UINTN)Uint8Buffer - (UINTN)Buffer;
  }

  //
  // Restore Debug Timer interrupt
  //
  SaveAndSetDebugTimerInterrupt (DebugTimerInterruptState);

  //
  // Restore to original TPL
  //
  gBS->RestoreTPL (Tpl);

  return EFI_SUCCESS;
}
Пример #6
0
/**
  Read the specified number of bytes from serial device.

  @param[in] This            Pointer to EFI_SERIAL_IO_PROTOCOL.
  @param[in, out] BufferSize On input the size of Buffer, on output the amount of
                             data returned in buffer.
  @param[out] Buffer         The buffer to return the data into.

  @retval EFI_SUCCESS        The data were read successfully.
  @retval EFI_DEVICE_ERROR   The device reported an error.
  @retval EFI_TIMEOUT        The read operation was stopped due to timeout.

**/
EFI_STATUS
EFIAPI
SerialRead (
  IN EFI_SERIAL_IO_PROTOCOL  *This,
  IN OUT UINTN               *BufferSize,
  OUT VOID                   *Buffer
  )
{
  EFI_STATUS                  Status;
  UINTN                       Index;
  UINT8                       *Uint8Buffer;
  BOOLEAN                     OldInterruptState;
  DEBUG_PORT_HANDLE           Handle;
  UINT8                       Data;

  Handle = GetDebugPortHandle ();

  //
  // Save and disable Debug Timer interrupt to avoid it to access Debug Port
  //
  OldInterruptState = SaveAndSetDebugTimerInterrupt (FALSE);
  
  Uint8Buffer = (UINT8 *)Buffer;
  if ((mSerialIoMode.ControlMask & EFI_SERIAL_SOFTWARE_LOOPBACK_ENABLE) != 0)  {
    if ((mLoopbackBuffer & SERIAL_PORT_LOOPBACK_BUFFER_FULL) == 0) {
      return EFI_TIMEOUT;
    }
    *Uint8Buffer = (UINT8)(mLoopbackBuffer & 0xff);
    mLoopbackBuffer = 0;
    *BufferSize = 1;
  } else {
    for (Index = 0; Index < *BufferSize; Index++) {
      //
      // Read input character from terminal FIFO firstly
      //
      Status = DebugTerminalFifoRemove (&mSerialFifoForTerminal, &Data);
      if (Status == EFI_SUCCESS) {
        *Uint8Buffer = Data;
        Uint8Buffer ++;
        continue;
      }
      //
      // Read the input character from Debug Port 
      //
      if (!DebugPortPollBuffer (Handle)) {
        break;
      }
      DebugPortReadBuffer (Handle, &Data, 1, 0);

      if (Data== DEBUG_STARTING_SYMBOL_ATTACH ||
          Data == DEBUG_STARTING_SYMBOL_BREAK) {
        //
        // Add the debug symbol into Debug FIFO
        //
        DebugTerminalFifoAdd (&mSerialFifoForDebug, Data);
      } else {
        *Uint8Buffer = Data;
        Uint8Buffer ++;
      }
    }
    *BufferSize = (UINTN)Uint8Buffer - (UINTN)Buffer;
  }

  //
  // Restore Debug Timer interrupt
  //  
  SaveAndSetDebugTimerInterrupt (OldInterruptState);
  
  return EFI_SUCCESS;
}