/** @file
  Contains all EFI_UDP6_PROTOCOL interfaces.

  Copyright (c) 2009 - 2018, Intel Corporation. All rights reserved.<BR>

  SPDX-License-Identifier: BSD-2-Clause-Patent

**/

#include "Udp6Impl.h"

EFI_UDP6_PROTOCOL  mUdp6Protocol = {
  Udp6GetModeData,
  Udp6Configure,
  Udp6Groups,
  Udp6Transmit,
  Udp6Receive,
  Udp6Cancel,
  Udp6Poll
};

/**
  This function copies the current operational settings of this EFI UDPv6 Protocol
  instance into user-supplied buffers. This function is used optionally to retrieve
  the operational mode data of underlying networks or drivers.

  @param[in]  This               Pointer to the EFI_UDP6_PROTOCOL instance.
  @param[out] Udp6ConfigData     The buffer in which the current UDP configuration
                                 data is returned. This parameter is optional and
                                 may be NULL.
  @param[out] Ip6ModeData        The buffer in which the current EFI IPv6 Protocol
                                 mode data is returned. This parameter is optional
                                 and may be NULL.
  @param[out] MnpConfigData      The buffer in which the current managed network
                                 configuration data is returned. This parameter is
                                 optional and may be NULL.
  @param[out] SnpModeData        The buffer in which the simple network mode data
                                 is returned. This parameter is optional and may be NULL.

  @retval EFI_SUCCESS            The mode data was read.
  @retval EFI_NOT_STARTED        When Udp6ConfigData is queried, no configuration
                                 data is  available because this instance has not
                                 been started.
  @retval EFI_INVALID_PARAMETER  This is NULL.

**/
EFI_STATUS
EFIAPI
Udp6GetModeData (
  IN  EFI_UDP6_PROTOCOL                *This,
  OUT EFI_UDP6_CONFIG_DATA             *Udp6ConfigData OPTIONAL,
  OUT EFI_IP6_MODE_DATA                *Ip6ModeData    OPTIONAL,
  OUT EFI_MANAGED_NETWORK_CONFIG_DATA  *MnpConfigData  OPTIONAL,
  OUT EFI_SIMPLE_NETWORK_MODE          *SnpModeData    OPTIONAL
  )
{
  UDP6_INSTANCE_DATA  *Instance;
  EFI_IP6_PROTOCOL    *Ip;
  EFI_TPL             OldTpl;
  EFI_STATUS          Status;

  if (This == NULL) {
    return EFI_INVALID_PARAMETER;
  }

  Instance = UDP6_INSTANCE_DATA_FROM_THIS (This);

  if (!Instance->Configured && (Udp6ConfigData != NULL)) {
    return EFI_NOT_STARTED;
  }

  OldTpl = gBS->RaiseTPL (TPL_CALLBACK);

  if (Udp6ConfigData != NULL) {
    //
    // Set the Udp6ConfigData.
    //
    CopyMem (Udp6ConfigData, &Instance->ConfigData, sizeof (EFI_UDP6_CONFIG_DATA));
  }

  Ip = Instance->IpInfo->Ip.Ip6;

  //
  // Get the underlying Ip6ModeData, MnpConfigData and SnpModeData.
  //
  Status = Ip->GetModeData (Ip, Ip6ModeData, MnpConfigData, SnpModeData);

  gBS->RestoreTPL (OldTpl);

  return Status;
}

/**
  This function is used to do the following:
  Initialize and start this instance of the EFI UDPv6 Protocol.
  Change the filtering rules and operational parameters.
  Reset this instance of the EFI UDPv6 Protocol.

  @param[in]  This               Pointer to the EFI_UDP6_PROTOCOL instance.
  @param[in]  UdpConfigData      Pointer to the buffer to set the configuration
                                 data. This parameter is optional and may be NULL.

  @retval EFI_SUCCESS            The configuration settings were set, changed, or
                                 reset successfully.
  @retval EFI_NO_MAPPING         When the UdpConfigData.UseAnyStationAddress is set
                                 to true and there is no address available for the IP6
                                 driver to bind a source address to this instance.
  @retval EFI_INVALID_PARAMETER  One or more following conditions are TRUE:
                                 This is NULL.
                                 UdpConfigData.StationAddress is not a valid
                                 unicast IPv6 address.
                                 UdpConfigData.RemoteAddress is not a valid unicast
                                 IPv6  address if it is not zero.
  @retval EFI_ALREADY_STARTED    The EFI UDPv6 Protocol instance is already
                                 started/configured and must be stopped/reset
                                 before it can be reconfigured. Only TrafficClass,
                                 HopLimit, ReceiveTimeout, and  TransmitTimeout can
                                 be reconfigured without stopping the  current
                                 instance of the EFI UDPv6 Protocol.
  @retval EFI_ACCESS_DENIED      UdpConfigData.AllowDuplicatePort is FALSE and
                                 UdpConfigData.StationPort is already used by another
                                 instance.
  @retval EFI_OUT_OF_RESOURCES   The EFI UDPv6 Protocol driver cannot allocate
                                 memory for this EFI UDPv6 Protocol instance.
  @retval EFI_DEVICE_ERROR       An unexpected network or system error occurred, and
                                 this instance was not opened.

**/
EFI_STATUS
EFIAPI
Udp6Configure (
  IN EFI_UDP6_PROTOCOL     *This,
  IN EFI_UDP6_CONFIG_DATA  *UdpConfigData OPTIONAL
  )
{
  EFI_STATUS           Status;
  UDP6_INSTANCE_DATA   *Instance;
  UDP6_SERVICE_DATA    *Udp6Service;
  EFI_TPL              OldTpl;
  EFI_IPv6_ADDRESS     StationAddress;
  EFI_IPv6_ADDRESS     RemoteAddress;
  EFI_IP6_CONFIG_DATA  Ip6ConfigData;
  EFI_IPv6_ADDRESS     LocalAddr;
  EFI_IPv6_ADDRESS     RemoteAddr;

  if (This == NULL) {
    return EFI_INVALID_PARAMETER;
  }

  Instance = UDP6_INSTANCE_DATA_FROM_THIS (This);

  if (!Instance->Configured && (UdpConfigData == NULL)) {
    return EFI_SUCCESS;
  }

  Udp6Service = Instance->Udp6Service;
  Status      = EFI_SUCCESS;
  ASSERT (Udp6Service != NULL);

  OldTpl = gBS->RaiseTPL (TPL_CALLBACK);

  if (UdpConfigData != NULL) {
    IP6_COPY_ADDRESS (&StationAddress, &UdpConfigData->StationAddress);
    IP6_COPY_ADDRESS (&RemoteAddress, &UdpConfigData->RemoteAddress);

    if ((!NetIp6IsUnspecifiedAddr (&StationAddress) && !NetIp6IsValidUnicast (&StationAddress)) ||
        (!NetIp6IsUnspecifiedAddr (&RemoteAddress) && !NetIp6IsValidUnicast (&RemoteAddress))
        )
    {
      //
      // If not use default address, and StationAddress is not a valid unicast
      // if it is not IPv6 address or RemoteAddress is not a valid unicast IPv6
      // address if it is not 0.
      //
      Status = EFI_INVALID_PARAMETER;
      goto ON_EXIT;
    }

    if (Instance->Configured) {
      //
      // The instance is already configured, try to do the re-configuration.
      //
      if (!Udp6IsReconfigurable (&Instance->ConfigData, UdpConfigData)) {
        //
        // If the new configuration data wants to change some unreconfigurable
        // settings, return EFI_ALREADY_STARTED.
        //
        Status = EFI_ALREADY_STARTED;
        goto ON_EXIT;
      }

      //
      // Save the reconfigurable parameters.
      //
      Instance->ConfigData.TrafficClass    = UdpConfigData->TrafficClass;
      Instance->ConfigData.HopLimit        = UdpConfigData->HopLimit;
      Instance->ConfigData.ReceiveTimeout  = UdpConfigData->ReceiveTimeout;
      Instance->ConfigData.TransmitTimeout = UdpConfigData->TransmitTimeout;
    } else {
      //
      // Construct the Ip configuration data from the UdpConfigData.
      //
      Udp6BuildIp6ConfigData (UdpConfigData, &Ip6ConfigData);

      //
      // Configure the Ip instance wrapped in the IpInfo.
      //
      Status = IpIoConfigIp (Instance->IpInfo, &Ip6ConfigData);
      if (EFI_ERROR (Status)) {
        if (Status == EFI_NO_MAPPING) {
          Instance->IsNoMapping = TRUE;
        }

        goto ON_EXIT;
      }

      Instance->IsNoMapping = FALSE;

      //
      // Save the configuration data.
      //
      CopyMem (
        &Instance->ConfigData,
        UdpConfigData,
        sizeof (EFI_UDP6_CONFIG_DATA)
        );
      IP6_COPY_ADDRESS (&Instance->ConfigData.StationAddress, &Ip6ConfigData.StationAddress);
      //
      // Try to allocate the required port resource.
      //
      Status = Udp6Bind (&Udp6Service->ChildrenList, &Instance->ConfigData);
      if (EFI_ERROR (Status)) {
        //
        // Reset the ip instance if bind fails.
        //
        IpIoConfigIp (Instance->IpInfo, NULL);
        goto ON_EXIT;
      }

      //
      // Pre calculate the checksum for the pseudo head, ignore the UDP length first.
      //
      IP6_COPY_ADDRESS (&LocalAddr, &Instance->ConfigData.StationAddress);
      IP6_COPY_ADDRESS (&RemoteAddr, &Instance->ConfigData.RemoteAddress);

      Instance->HeadSum = NetIp6PseudoHeadChecksum (
                            &LocalAddr,
                            &RemoteAddr,
                            EFI_IP_PROTO_UDP,
                            0
                            );

      Instance->Configured = TRUE;
    }
  } else {
    //
    // UdpConfigData is NULL, reset the instance.
    //
    Instance->Configured  = FALSE;
    Instance->IsNoMapping = FALSE;

    //
    // Reset the Ip instance wrapped in the IpInfo.
    //
    IpIoConfigIp (Instance->IpInfo, NULL);

    //
    // Cancel all the user tokens.
    //
    Instance->Udp6Proto.Cancel (&Instance->Udp6Proto, NULL);

    //
    // Remove the buffered RxData for this instance.
    //
    Udp6FlushRcvdDgram (Instance);

    ASSERT (IsListEmpty (&Instance->DeliveredDgramQue));
  }

ON_EXIT:

  gBS->RestoreTPL (OldTpl);

  return Status;
}

/**
  This function is used to enable and disable the multicast group filtering.

  @param[in]  This               Pointer to the EFI_UDP6_PROTOCOL instance.
  @param[in]  JoinFlag           Set to TRUE to join a multicast group. Set to
                                 FALSE to leave one or all multicast groups.
  @param[in]  MulticastAddress   Pointer to multicast group address to join or
                                 leave. This parameter is optional and may be NULL.

  @retval EFI_SUCCESS            The operation completed successfully.
  @retval EFI_NOT_STARTED        The EFI UDPv6 Protocol instance has not been
                                 started.
  @retval EFI_OUT_OF_RESOURCES   Could not allocate resources to join the group.
  @retval EFI_INVALID_PARAMETER  One or more of the following conditions is TRUE:
                                 This is NULL.
                                 JoinFlag is TRUE and MulticastAddress is NULL.
                                 JoinFlag is TRUE and *MulticastAddress is not a
                                 valid  multicast address.
  @retval EFI_ALREADY_STARTED    The group address is already in the group table
                                 (when JoinFlag is TRUE).
  @retval EFI_NOT_FOUND          The group address is not in the group table (when
                                 JoinFlag is FALSE).
  @retval EFI_DEVICE_ERROR       An unexpected system or network error occurred.

**/
EFI_STATUS
EFIAPI
Udp6Groups (
  IN EFI_UDP6_PROTOCOL  *This,
  IN BOOLEAN            JoinFlag,
  IN EFI_IPv6_ADDRESS   *MulticastAddress OPTIONAL
  )
{
  EFI_STATUS          Status;
  UDP6_INSTANCE_DATA  *Instance;
  EFI_IP6_PROTOCOL    *Ip;
  EFI_TPL             OldTpl;
  EFI_IPv6_ADDRESS    *McastIp;

  if ((This == NULL) || (JoinFlag && (MulticastAddress == NULL))) {
    return EFI_INVALID_PARAMETER;
  }

  McastIp = NULL;

  if (JoinFlag) {
    if (!IP6_IS_MULTICAST (MulticastAddress)) {
      return EFI_INVALID_PARAMETER;
    }

    McastIp = AllocateCopyPool (sizeof (EFI_IPv6_ADDRESS), MulticastAddress);
    if (McastIp == NULL) {
      return EFI_OUT_OF_RESOURCES;
    }
  }

  Instance = UDP6_INSTANCE_DATA_FROM_THIS (This);
  if (!Instance->Configured) {
    if (McastIp != NULL) {
      FreePool (McastIp);
    }

    return EFI_NOT_STARTED;
  }

  Ip = Instance->IpInfo->Ip.Ip6;

  OldTpl = gBS->RaiseTPL (TPL_CALLBACK);

  //
  // Invoke the Ip instance the Udp6 instance consumes to do the group operation.
  //
  Status = Ip->Groups (Ip, JoinFlag, MulticastAddress);

  if (EFI_ERROR (Status)) {
    goto ON_EXIT;
  }

  //
  // Keep a local copy of the configured multicast IPs because IpIo receives
  // datagrams from the 0 station address IP instance and then UDP delivers to
  // the matched instance. This copy of multicast IPs is used to avoid receive
  // the multicast datagrams destinated to multicast IPs the other instances configured.
  //
  if (JoinFlag) {
    Status = NetMapInsertTail (&Instance->McastIps, (VOID *)McastIp, NULL);
  } else {
    Status = NetMapIterate (&Instance->McastIps, Udp6LeaveGroup, MulticastAddress);
    if ((MulticastAddress != NULL) && (Status == EFI_ABORTED)) {
      Status = EFI_SUCCESS;
    }
  }

ON_EXIT:

  gBS->RestoreTPL (OldTpl);

  if (EFI_ERROR (Status)) {
    if (McastIp != NULL) {
      FreePool (McastIp);
    }
  }

  return Status;
}

/**
  This function places a sending request to this instance of the EFI UDPv6 Protocol,
  alongside the transmit data that was filled by the user.

  @param[in]  This               Pointer to the EFI_UDP6_PROTOCOL instance.
  @param[in]  Token              Pointer to the completion token that will be
                                 placed into the transmit queue.

  @retval EFI_SUCCESS            The data was queued for transmission.
  @retval EFI_NOT_STARTED        This EFI UDPv6 Protocol instance has not been
                                 started.
  @retval EFI_NO_MAPPING         The under-layer IPv6 driver was responsible for
                                 choosing a source address for this instance, but
                                 no  source address was available for use.
  @retval EFI_INVALID_PARAMETER  One or more of the following are TRUE:
                                 This is NULL.
                                 Token is NULL. Token.Event is NULL.
                                 Token.Packet.TxData is NULL.
                                 Token.Packet.TxData.FragmentCount is zero.
                                 Token.Packet.TxData.DataLength is not equal to the
                                 sum of fragment lengths.
                                 One or more of the
                                 Token.Packet.TxData.FragmentTable[].FragmentLength
                                 fields is zero.
                                 One or more of the
                                 Token.Packet.TxData.FragmentTable[].FragmentBuffer
                                 fields is NULL. One or more of the
                                 Token.Packet.TxData.UdpSessionData.DestinationAddress
                                 are not valid unicast IPv6
                                 addresses if the  UdpSessionData is not NULL.
                                 Token.Packet.TxData.UdpSessionData.
                                 DestinationAddress is NULL
                                 Token.Packet.TxData.UdpSessionData.
                                 DestinationPort
                                 is zero.
                                 Token.Packet.TxData.UdpSessionData is NULL and this
                                 instance's UdpConfigData.RemoteAddress  is unspecified.
  @retval EFI_ACCESS_DENIED      The transmit completion token with the same
                                 Token.Event is already in the transmit queue.
  @retval EFI_NOT_READY          The completion token could not be queued because
                                 the transmit queue is full.
  @retval EFI_OUT_OF_RESOURCES   Could not queue the transmit data.
  @retval EFI_NOT_FOUND          There is no route to the destination network or
                                 address.
  @retval EFI_BAD_BUFFER_SIZE    The data length is greater than the maximum UDP
                                 packet size. Or, the length of the IP header + UDP
                                 header + data length is greater than MTU if
                                 DoNotFragment is TRUE.

**/
EFI_STATUS
EFIAPI
Udp6Transmit (
  IN EFI_UDP6_PROTOCOL          *This,
  IN EFI_UDP6_COMPLETION_TOKEN  *Token
  )
{
  EFI_STATUS              Status;
  UDP6_INSTANCE_DATA      *Instance;
  EFI_TPL                 OldTpl;
  NET_BUF                 *Packet;
  EFI_UDP_HEADER          *Udp6Header;
  EFI_UDP6_CONFIG_DATA    *ConfigData;
  EFI_IPv6_ADDRESS        Source;
  EFI_IPv6_ADDRESS        Destination;
  EFI_UDP6_TRANSMIT_DATA  *TxData;
  EFI_UDP6_SESSION_DATA   *UdpSessionData;
  UDP6_SERVICE_DATA       *Udp6Service;
  IP_IO_OVERRIDE          Override;
  UINT16                  HeadSum;
  EFI_IP_ADDRESS          IpDestAddr;

  if ((This == NULL) || (Token == NULL)) {
    return EFI_INVALID_PARAMETER;
  }

  Instance = UDP6_INSTANCE_DATA_FROM_THIS (This);

  if (!Instance->Configured) {
    return EFI_NOT_STARTED;
  }

  OldTpl = gBS->RaiseTPL (TPL_CALLBACK);

  //
  // Validate the Token, if the token is invalid return the error code.
  //
  Status = Udp6ValidateTxToken (Instance, Token);
  if (EFI_ERROR (Status)) {
    goto ON_EXIT;
  }

  if (EFI_ERROR (NetMapIterate (&Instance->TxTokens, Udp6TokenExist, Token)) ||
      EFI_ERROR (NetMapIterate (&Instance->RxTokens, Udp6TokenExist, Token))
      )
  {
    //
    // Try to find a duplicate token in the two token maps, if found, return
    // EFI_ACCESS_DENIED.
    //
    Status = EFI_ACCESS_DENIED;
    goto ON_EXIT;
  }

  TxData = Token->Packet.TxData;

  //
  // Create a net buffer to hold the user buffer and the udp header.
  //
  Packet = NetbufFromExt (
             (NET_FRAGMENT *)TxData->FragmentTable,
             TxData->FragmentCount,
             UDP6_HEADER_SIZE,
             0,
             Udp6NetVectorExtFree,
             NULL
             );
  if (Packet == NULL) {
    Status = EFI_OUT_OF_RESOURCES;
    goto ON_EXIT;
  }

  //
  // Store the IpIo in ProtoData.
  //
  Udp6Service                       = Instance->Udp6Service;
  *((UINTN *)&Packet->ProtoData[0]) = (UINTN)(Udp6Service->IpIo);

  Udp6Header = (EFI_UDP_HEADER *)NetbufAllocSpace (Packet, UDP6_HEADER_SIZE, TRUE);
  ASSERT (Udp6Header != NULL);
  if (Udp6Header == NULL) {
    Status = EFI_OUT_OF_RESOURCES;
    goto ON_EXIT;
  }

  ConfigData = &Instance->ConfigData;

  //
  // Fill the udp header.
  //
  Udp6Header->SrcPort  = HTONS (ConfigData->StationPort);
  Udp6Header->DstPort  = HTONS (ConfigData->RemotePort);
  Udp6Header->Length   = HTONS ((UINT16)Packet->TotalSize);
  Udp6Header->Checksum = 0;
  //
  // Set the UDP Header in NET_BUF, this UDP header is for IP6 can fast get the
  // Udp header for pseudoHeadCheckSum.
  //
  Packet->Udp    = Udp6Header;
  UdpSessionData = TxData->UdpSessionData;

  if (UdpSessionData != NULL) {
    //
    // Set the Destination according to the specified
    // UdpSessionData.
    //

    if (UdpSessionData->DestinationPort != 0) {
      Udp6Header->DstPort = HTONS (UdpSessionData->DestinationPort);
    }

    IP6_COPY_ADDRESS (&Source, &ConfigData->StationAddress);
    if (!NetIp6IsUnspecifiedAddr (&UdpSessionData->DestinationAddress)) {
      IP6_COPY_ADDRESS (&Destination, &UdpSessionData->DestinationAddress);
    } else {
      IP6_COPY_ADDRESS (&Destination, &ConfigData->RemoteAddress);
    }

    //
    // Calculate the pseudo head checksum using the overridden parameters.
    //
    if (!NetIp6IsUnspecifiedAddr (&ConfigData->StationAddress)) {
      HeadSum = NetIp6PseudoHeadChecksum (
                  &Source,
                  &Destination,
                  EFI_IP_PROTO_UDP,
                  0
                  );

      //
      // calculate the checksum.
      //
      Udp6Header->Checksum = Udp6Checksum (Packet, HeadSum);
      if (Udp6Header->Checksum == 0) {
        //
        // If the calculated checksum is 0, fill the Checksum field with all ones.
        //
        Udp6Header->Checksum = 0xffff;
      }
    } else {
      //
      // Set the checksum is zero if the ConfigData->StationAddress is unspecified
      // and the Ipv6 will fill the correct value of this checksum.
      //
      Udp6Header->Checksum = 0;
    }
  } else {
    //
    // UdpSessionData is NULL, use the address and port information previously configured.
    //
    IP6_COPY_ADDRESS (&Destination, &ConfigData->RemoteAddress);

    HeadSum = Instance->HeadSum;
    //
    // calculate the checksum.
    //
    Udp6Header->Checksum = Udp6Checksum (Packet, HeadSum);
    if (Udp6Header->Checksum == 0) {
      //
      // If the calculated checksum is 0, fill the Checksum field with all ones.
      //
      Udp6Header->Checksum = 0xffff;
    }
  }

  //
  // Fill the IpIo Override data.
  //
  Override.Ip6OverrideData.Protocol  = EFI_IP_PROTO_UDP;
  Override.Ip6OverrideData.HopLimit  = ConfigData->HopLimit;
  Override.Ip6OverrideData.FlowLabel = 0;

  //
  // Save the token into the TxToken map.
  //
  Status = NetMapInsertTail (&Instance->TxTokens, Token, Packet);
  if (EFI_ERROR (Status)) {
    goto FREE_PACKET;
  }

  //
  // Send out this datagram through IpIo.
  //
  if (UdpSessionData != NULL) {
    IP6_COPY_ADDRESS (&(IpDestAddr.v6), &Destination);
  } else {
    ZeroMem (&IpDestAddr.v6, sizeof (EFI_IPv6_ADDRESS));
  }

  Status = IpIoSend (
             Udp6Service->IpIo,
             Packet,
             Instance->IpInfo,
             Instance,
             Token,
             &IpDestAddr,
             &Override
             );
  if (EFI_ERROR (Status)) {
    //
    // Remove this token from the TxTokens.
    //
    Udp6RemoveToken (&Instance->TxTokens, Token);
  }

FREE_PACKET:

  NetbufFree (Packet);

ON_EXIT:

  gBS->RestoreTPL (OldTpl);

  return Status;
}

/**
  This function places a completion token into the receive packet queue. This function
  is always asynchronous.

  @param[in]  This               Pointer to the EFI_UDP6_PROTOCOL instance.
  @param[in]  Token              Pointer to a token that is associated with the
                                 receive data descriptor.

  @retval EFI_SUCCESS            The receive completion token was cached.
  @retval EFI_NOT_STARTED        This EFI UDPv6 Protocol instance has not been
                                 started.
  @retval EFI_NO_MAPPING         When using a default address, configuration (DHCP,
                                 BOOTP, RARP, etc.) is not finished yet.
  @retval EFI_INVALID_PARAMETER  One or more of the following conditions is TRUE:
                                 This is NULL. Token is NULL. Token.Event is NULL.
  @retval EFI_OUT_OF_RESOURCES   The receive completion token could not be queued
                                 due to a lack of system resources (usually
                                 memory).
  @retval EFI_DEVICE_ERROR       An unexpected system or network error occurred.
                                 The EFI UDPv6 Protocol instance has been reset to
                                 startup defaults.
  @retval EFI_ACCESS_DENIED      A receive completion token with the same
                                 Token.Event is already in the receive queue.
  @retval EFI_NOT_READY          The receive request could not be queued because
                                 the receive  queue is full.

**/
EFI_STATUS
EFIAPI
Udp6Receive (
  IN EFI_UDP6_PROTOCOL          *This,
  IN EFI_UDP6_COMPLETION_TOKEN  *Token
  )
{
  EFI_STATUS          Status;
  UDP6_INSTANCE_DATA  *Instance;
  EFI_TPL             OldTpl;

  if ((This == NULL) || (Token == NULL) || (Token->Event == NULL)) {
    return EFI_INVALID_PARAMETER;
  }

  Instance = UDP6_INSTANCE_DATA_FROM_THIS (This);

  if (!Instance->Configured) {
    return EFI_NOT_STARTED;
  }

  OldTpl = gBS->RaiseTPL (TPL_CALLBACK);

  if (EFI_ERROR (NetMapIterate (&Instance->RxTokens, Udp6TokenExist, Token)) ||
      EFI_ERROR (NetMapIterate (&Instance->TxTokens, Udp6TokenExist, Token))
      )
  {
    //
    // Return EFI_ACCESS_DENIED if the specified token is already in the TxTokens or
    // RxTokens map.
    //
    Status = EFI_ACCESS_DENIED;
    goto ON_EXIT;
  }

  Token->Packet.RxData = NULL;

  //
  // Save the token into the RxTokens map.
  //
  Status = NetMapInsertTail (&Instance->RxTokens, Token, NULL);
  if (EFI_ERROR (Status)) {
    Status = EFI_NOT_READY;
    goto ON_EXIT;
  }

  //
  // If there is an icmp error, report it.
  //
  Udp6ReportIcmpError (Instance);

  //
  // Try to delivered the received datagrams.
  //
  Udp6InstanceDeliverDgram (Instance);

  //
  // Dispatch the DPC queued by the NotifyFunction of Token->Event.
  //
  DispatchDpc ();

ON_EXIT:

  gBS->RestoreTPL (OldTpl);

  return Status;
}

/**
  This function is used to abort a pending transmit or receive request.

  @param[in]  This               Pointer to the EFI_UDP6_PROTOCOL instance.
  @param[in]  Token              Pointer to a token that has been issued by
                                 EFI_UDP6_PROTOCOL.Transmit() or
                                 EFI_UDP6_PROTOCOL.Receive(). This parameter is
                                 optional and may be NULL.

  @retval EFI_SUCCESS            The asynchronous I/O request was aborted, and
                                 Token.Event was  signaled. When Token is NULL, all
                                 pending requests are aborted and their events are
                                 signaled.
  @retval EFI_INVALID_PARAMETER  This is NULL.
  @retval EFI_NOT_STARTED        This instance has not been started.
  @retval EFI_NO_MAPPING         When using the default address, configuration
                                 (DHCP, BOOTP, RARP, etc.) is not finished yet.
  @retval EFI_NOT_FOUND          When Token is not NULL, the asynchronous I/O
                                 request is not found in the transmit or receive
                                 queue. It is either completed or not issued by
                                 Transmit() or Receive().

**/
EFI_STATUS
EFIAPI
Udp6Cancel (
  IN EFI_UDP6_PROTOCOL          *This,
  IN EFI_UDP6_COMPLETION_TOKEN  *Token OPTIONAL
  )
{
  EFI_STATUS          Status;
  UDP6_INSTANCE_DATA  *Instance;
  EFI_TPL             OldTpl;

  if (This == NULL) {
    return EFI_INVALID_PARAMETER;
  }

  Instance = UDP6_INSTANCE_DATA_FROM_THIS (This);

  if (!Instance->Configured) {
    return EFI_NOT_STARTED;
  }

  OldTpl = gBS->RaiseTPL (TPL_CALLBACK);

  //
  // Cancel the tokens specified by Token for this instance.
  //
  Status = Udp6InstanceCancelToken (Instance, Token);

  //
  // Dispatch the DPC queued by the NotifyFunction of the canceled token's events.
  //
  DispatchDpc ();

  gBS->RestoreTPL (OldTpl);

  return Status;
}

/**
  This function can be used by network drivers and applications to increase the rate that
  data packets are moved between the communications device and the transmit/receive queues.

  @param[in] This                Pointer to the EFI_UDP6_PROTOCOL instance.

  @retval EFI_SUCCESS            Incoming or outgoing data was processed.
  @retval EFI_INVALID_PARAMETER  This is NULL.
  @retval EFI_DEVICE_ERROR       An unexpected system or network error occurred.
  @retval EFI_TIMEOUT            Data was dropped out of the transmit and/or
                                 receive queue.

**/
EFI_STATUS
EFIAPI
Udp6Poll (
  IN EFI_UDP6_PROTOCOL  *This
  )
{
  UDP6_INSTANCE_DATA  *Instance;
  EFI_IP6_PROTOCOL    *Ip;

  if (This == NULL) {
    return EFI_INVALID_PARAMETER;
  }

  Instance = UDP6_INSTANCE_DATA_FROM_THIS (This);
  Ip       = Instance->IpInfo->Ip.Ip6;

  //
  // Invode the Ip instance consumed by the udp instance to do the poll operation.
  //
  return Ip->Poll (Ip);
}
