/** @file
  Function to validate, parse, process the DHCP options.

Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent

**/

#include "Dhcp4Impl.h"

///
/// A list of the format of DHCP Options sorted by option tag
/// to validate a dhcp message. Refere the comments of the
/// DHCP_OPTION_FORMAT structure.
///
DHCP_OPTION_FORMAT  DhcpOptionFormats[] = {
  { DHCP4_TAG_NETMASK,         DHCP_OPTION_IP,     1, 1,  TRUE  },
  { DHCP4_TAG_TIME_OFFSET,     DHCP_OPTION_INT32,  1, 1,  FALSE },
  { DHCP4_TAG_ROUTER,          DHCP_OPTION_IP,     1, -1, TRUE  },
  { DHCP4_TAG_TIME_SERVER,     DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_NAME_SERVER,     DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_DNS_SERVER,      DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_LOG_SERVER,      DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_COOKIE_SERVER,   DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_LPR_SERVER,      DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_IMPRESS_SERVER,  DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_RL_SERVER,       DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_HOSTNAME,        DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_BOOTFILE_LEN,    DHCP_OPTION_INT16,  1, 1,  FALSE },
  { DHCP4_TAG_DUMP,            DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_DOMAINNAME,      DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_SWAP_SERVER,     DHCP_OPTION_IP,     1, 1,  FALSE },
  { DHCP4_TAG_ROOTPATH,        DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_EXTEND_PATH,     DHCP_OPTION_INT8,   1, -1, FALSE },

  { DHCP4_TAG_IPFORWARD,       DHCP_OPTION_SWITCH, 1, 1,  FALSE },
  { DHCP4_TAG_NONLOCAL_SRR,    DHCP_OPTION_SWITCH, 1, 1,  FALSE },
  { DHCP4_TAG_POLICY_SRR,      DHCP_OPTION_IPPAIR, 1, -1, FALSE },
  { DHCP4_TAG_EMTU,            DHCP_OPTION_INT16,  1, 1,  FALSE },
  { DHCP4_TAG_TTL,             DHCP_OPTION_INT8,   1, 1,  FALSE },
  { DHCP4_TAG_PATHMTU_AGE,     DHCP_OPTION_INT32,  1, 1,  FALSE },
  { DHCP4_TAG_PATHMTU_PLATEAU, DHCP_OPTION_INT16,  1, -1, FALSE },

  { DHCP4_TAG_IFMTU,           DHCP_OPTION_INT16,  1, 1,  FALSE },
  { DHCP4_TAG_SUBNET_LOCAL,    DHCP_OPTION_SWITCH, 1, 1,  FALSE },
  { DHCP4_TAG_BROADCAST,       DHCP_OPTION_IP,     1, 1,  FALSE },
  { DHCP4_TAG_DISCOVER_MASK,   DHCP_OPTION_SWITCH, 1, 1,  FALSE },
  { DHCP4_TAG_SUPPLY_MASK,     DHCP_OPTION_SWITCH, 1, 1,  FALSE },
  { DHCP4_TAG_DISCOVER_ROUTE,  DHCP_OPTION_SWITCH, 1, 1,  FALSE },
  { DHCP4_TAG_ROUTER_SOLICIT,  DHCP_OPTION_IP,     1, 1,  FALSE },
  { DHCP4_TAG_STATIC_ROUTE,    DHCP_OPTION_IPPAIR, 1, -1, FALSE },

  { DHCP4_TAG_TRAILER,         DHCP_OPTION_SWITCH, 1, 1,  FALSE },
  { DHCP4_TAG_ARPAGE,          DHCP_OPTION_INT32,  1, 1,  FALSE },
  { DHCP4_TAG_ETHER_ENCAP,     DHCP_OPTION_SWITCH, 1, 1,  FALSE },

  { DHCP4_TAG_TCP_TTL,         DHCP_OPTION_INT8,   1, 1,  FALSE },
  { DHCP4_TAG_KEEP_INTERVAL,   DHCP_OPTION_INT32,  1, 1,  FALSE },
  { DHCP4_TAG_KEEP_GARBAGE,    DHCP_OPTION_SWITCH, 1, 1,  FALSE },

  { DHCP4_TAG_NIS_DOMAIN,      DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_NIS_SERVER,      DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_NTP_SERVER,      DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_VENDOR,          DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_NBNS,            DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_NBDD,            DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_NBTYPE,          DHCP_OPTION_INT8,   1, 1,  FALSE },
  { DHCP4_TAG_NBSCOPE,         DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_XFONT,           DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_XDM,             DHCP_OPTION_IP,     1, -1, FALSE },

  { DHCP4_TAG_REQUEST_IP,      DHCP_OPTION_IP,     1, 1,  FALSE },
  { DHCP4_TAG_LEASE,           DHCP_OPTION_INT32,  1, 1,  TRUE  },
  { DHCP4_TAG_OVERLOAD,        DHCP_OPTION_INT8,   1, 1,  TRUE  },
  { DHCP4_TAG_MSG_TYPE,        DHCP_OPTION_INT8,   1, 1,  TRUE  },
  { DHCP4_TAG_SERVER_ID,       DHCP_OPTION_IP,     1, 1,  TRUE  },
  { DHCP4_TAG_PARA_LIST,       DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_MESSAGE,         DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_MAXMSG,          DHCP_OPTION_INT16,  1, 1,  FALSE },
  { DHCP4_TAG_T1,              DHCP_OPTION_INT32,  1, 1,  TRUE  },
  { DHCP4_TAG_T2,              DHCP_OPTION_INT32,  1, 1,  TRUE  },
  { DHCP4_TAG_VENDOR_CLASS_ID, DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_CLIENT_ID,       DHCP_OPTION_INT8,   2, -1, FALSE },

  { DHCP4_TAG_NISPLUS,         DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_NISPLUS_SERVER,  DHCP_OPTION_IP,     1, -1, FALSE },

  { DHCP4_TAG_TFTP,            DHCP_OPTION_INT8,   1, -1, FALSE },
  { DHCP4_TAG_BOOTFILE,        DHCP_OPTION_INT8,   1, -1, FALSE },

  { DHCP4_TAG_MOBILEIP,        DHCP_OPTION_IP,     0, -1, FALSE },
  { DHCP4_TAG_SMTP,            DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_POP3,            DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_NNTP,            DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_WWW,             DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_FINGER,          DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_IRC,             DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_STTALK,          DHCP_OPTION_IP,     1, -1, FALSE },
  { DHCP4_TAG_STDA,            DHCP_OPTION_IP,     1, -1, FALSE },

  { DHCP4_TAG_CLASSLESS_ROUTE, DHCP_OPTION_INT8,   5, -1, FALSE },
};

/**
  Binary search the DhcpOptionFormats array to find the format
  information about a specific option.

  @param[in]  Tag                    The option's tag.

  @return The point to the option's format, NULL if not found.

**/
DHCP_OPTION_FORMAT *
DhcpFindOptionFormat (
  IN UINT8  Tag
  )
{
  INTN  Left;
  INTN  Right;
  INTN  Middle;

  Left  = 0;
  Right = sizeof (DhcpOptionFormats) / sizeof (DHCP_OPTION_FORMAT) - 1;

  while (Right >= Left) {
    Middle = (Left + Right) / 2;

    if (Tag == DhcpOptionFormats[Middle].Tag) {
      return &DhcpOptionFormats[Middle];
    }

    if (Tag < DhcpOptionFormats[Middle].Tag) {
      Right = Middle - 1;
    } else {
      Left = Middle + 1;
    }
  }

  return NULL;
}

/**
  Validate whether a single DHCP option is valid according to its format.

  @param[in]  Format                 The option's format
  @param[in]  OptValue               The value of the option
  @param[in]  Len                    The length of the option value

  @retval TRUE     The option is valid.
  @retval FALSE    Otherwise.

**/
BOOLEAN
DhcpOptionIsValid (
  IN DHCP_OPTION_FORMAT  *Format,
  IN UINT8               *OptValue,
  IN INTN                Len
  )
{
  INTN  Unit;
  INTN  Occur;
  INTN  Index;

  Unit = 0;

  switch (Format->Type) {
    case DHCP_OPTION_SWITCH:
    case DHCP_OPTION_INT8:
      Unit = 1;
      break;

    case DHCP_OPTION_INT16:
      Unit = 2;
      break;

    case DHCP_OPTION_INT32:
    case DHCP_OPTION_IP:
      Unit = 4;
      break;

    case DHCP_OPTION_IPPAIR:
      Unit = 8;
      break;
  }

  ASSERT (Unit != 0);

  //
  // Validate that the option appears in the full units.
  //
  if ((Len % Unit) != 0) {
    return FALSE;
  }

  //
  // Validate the occurrence of the option unit is with in [MinOccur, MaxOccur]
  //
  Occur = Len / Unit;

  if (((Format->MinOccur != -1) && (Occur < Format->MinOccur)) ||
      ((Format->MaxOccur != -1) && (Occur > Format->MaxOccur))
      )
  {
    return FALSE;
  }

  //
  // If the option is of type switch, only 0/1 are valid values.
  //
  if (Format->Type == DHCP_OPTION_SWITCH) {
    for (Index = 0; Index < Occur; Index++) {
      if ((OptValue[Index] != 0) && (OptValue[Index] != 1)) {
        return FALSE;
      }
    }
  }

  return TRUE;
}

/**
  Extract the client interested options, all the parameters are
  converted to host byte order.

  @param[in]  Tag                    The DHCP option tag
  @param[in]  Len                    The length of the option
  @param[in]  Data                   The value of the DHCP option
  @param[out] Para                   The variable to save the interested parameter

  @retval EFI_SUCCESS            The DHCP option is successfully extracted.
  @retval EFI_INVALID_PARAMETER  The DHCP option is mal-formatted

**/
EFI_STATUS
DhcpGetParameter (
  IN  UINT8           Tag,
  IN  INTN            Len,
  IN  UINT8           *Data,
  OUT DHCP_PARAMETER  *Para
  )
{
  switch (Tag) {
    case DHCP4_TAG_NETMASK:
      Para->NetMask = NetGetUint32 (Data);
      break;

    case DHCP4_TAG_ROUTER:
      //
      // Return the first router to consumer which is the preferred one
      //
      Para->Router = NetGetUint32 (Data);
      break;

    case DHCP4_TAG_LEASE:
      Para->Lease = NetGetUint32 (Data);
      break;

    case DHCP4_TAG_OVERLOAD:
      Para->Overload = *Data;

      if ((Para->Overload < 1) || (Para->Overload > 3)) {
        return EFI_INVALID_PARAMETER;
      }

      break;

    case DHCP4_TAG_MSG_TYPE:
      Para->DhcpType = *Data;

      if ((Para->DhcpType < 1) || (Para->DhcpType > 9)) {
        return EFI_INVALID_PARAMETER;
      }

      break;

    case DHCP4_TAG_SERVER_ID:
      Para->ServerId = NetGetUint32 (Data);
      break;

    case DHCP4_TAG_T1:
      Para->T1 = NetGetUint32 (Data);
      break;

    case DHCP4_TAG_T2:
      Para->T2 = NetGetUint32 (Data);
      break;
  }

  return EFI_SUCCESS;
}

/**
  Inspect all the options in a single buffer. DHCP options may be contained
  in several buffers, such as the BOOTP options filed, boot file or server
  name. Each option buffer is required to end with DHCP4_TAG_EOP.

  @param[in]  Buffer                 The buffer which contains DHCP options
  @param[in]  BufLen                 The length of the buffer
  @param[in]  Check                  The callback function for each option found
  @param[in]  Context                The opaque parameter for the Check
  @param[out] Overload               Variable to save the value of DHCP4_TAG_OVERLOAD
                                     option.

  @retval EFI_SUCCESS            All the options are valid
  @retval EFI_INVALID_PARAMETER  The options are mal-formatted.

**/
EFI_STATUS
DhcpIterateBufferOptions (
  IN  UINT8              *Buffer,
  IN  INTN               BufLen,
  IN  DHCP_CHECK_OPTION  Check             OPTIONAL,
  IN  VOID               *Context,
  OUT UINT8              *Overload         OPTIONAL
  )
{
  INTN   Cur;
  UINT8  Tag;
  UINT8  Len;

  Cur = 0;

  while (Cur < BufLen) {
    Tag = Buffer[Cur];

    if (Tag == DHCP4_TAG_PAD) {
      Cur++;
      continue;
    } else if (Tag == DHCP4_TAG_EOP) {
      return EFI_SUCCESS;
    }

    Cur++;

    if (Cur == BufLen) {
      return EFI_INVALID_PARAMETER;
    }

    Len = Buffer[Cur++];

    if (Cur + Len > BufLen) {
      return EFI_INVALID_PARAMETER;
    }

    if ((Tag == DHCP4_TAG_OVERLOAD) && (Overload != NULL)) {
      if (Len != 1) {
        return EFI_INVALID_PARAMETER;
      }

      *Overload = Buffer[Cur];
    }

    if ((Check != NULL) && EFI_ERROR (Check (Tag, Len, Buffer + Cur, Context))) {
      return EFI_INVALID_PARAMETER;
    }

    Cur += Len;
  }

  //
  // Each option buffer is expected to end with an EOP
  //
  return EFI_INVALID_PARAMETER;
}

/**
  Iterate through a DHCP message to visit each option. First inspect
  all the options in the OPTION field. Then if overloaded, inspect
  the options in FILENAME and SERVERNAME fields. One option may be
  encoded in several places. See RFC 3396 Encoding Long Options in DHCP

  @param[in]  Packet                 The DHCP packet to check the options for
  @param[in]  Check                  The callback function to be called for each option
                                     found
  @param[in]  Context                The opaque parameter for Check

  @retval EFI_SUCCESS            The DHCP packet's options are well formatted
  @retval EFI_INVALID_PARAMETER  The DHCP packet's options are not well formatted

**/
EFI_STATUS
DhcpIterateOptions (
  IN  EFI_DHCP4_PACKET   *Packet,
  IN  DHCP_CHECK_OPTION  Check         OPTIONAL,
  IN  VOID               *Context
  )
{
  EFI_STATUS  Status;
  UINT8       Overload;

  Overload = 0;

  Status = DhcpIterateBufferOptions (
             Packet->Dhcp4.Option,
             Packet->Length - sizeof (EFI_DHCP4_HEADER) - sizeof (UINT32),
             Check,
             Context,
             &Overload
             );

  if (EFI_ERROR (Status)) {
    return Status;
  }

  if ((Overload == DHCP_OVERLOAD_FILENAME) || (Overload == DHCP_OVERLOAD_BOTH)) {
    Status = DhcpIterateBufferOptions (
               (UINT8 *)Packet->Dhcp4.Header.BootFileName,
               128,
               Check,
               Context,
               NULL
               );

    if (EFI_ERROR (Status)) {
      return Status;
    }
  }

  if ((Overload == DHCP_OVERLOAD_SVRNAME) || (Overload == DHCP_OVERLOAD_BOTH)) {
    Status = DhcpIterateBufferOptions (
               (UINT8 *)Packet->Dhcp4.Header.ServerName,
               64,
               Check,
               Context,
               NULL
               );

    if (EFI_ERROR (Status)) {
      return Status;
    }
  }

  return EFI_SUCCESS;
}

/**
  Call back function to DhcpIterateOptions to compute each option's
  length. It just adds the data length of all the occurrences of this
  Tag. Context is an array of 256 DHCP_OPTION_COUNT.

  @param[in]  Tag                    The current option to check
  @param[in]  Len                    The length of the option data
  @param[in]  Data                   The option data
  @param[in]  Context                The context, which is a array of 256
                                     DHCP_OPTION_COUNT.

  @retval EFI_SUCCESS            It always returns EFI_SUCCESS.

**/
EFI_STATUS
DhcpGetOptionLen (
  IN UINT8  Tag,
  IN UINT8  Len,
  IN UINT8  *Data,
  IN VOID   *Context
  )
{
  DHCP_OPTION_COUNT  *OpCount;

  OpCount             = (DHCP_OPTION_COUNT *)Context;
  OpCount[Tag].Offset = (UINT16)(OpCount[Tag].Offset + Len);

  return EFI_SUCCESS;
}

/**
  Call back function to DhcpIterateOptions to consolidate each option's
  data. There are maybe several occurrence of the same option.

  @param[in]  Tag                    The option to consolidate its data
  @param[in]  Len                    The length of option data
  @param[in]  Data                   The data of the option's current occurrence
  @param[in]  Context                The context, which is DHCP_OPTION_CONTEXT. This
                                     array is  just a wrap to pass THREE parameters.

  @retval EFI_SUCCESS            It always returns EFI_SUCCESS

**/
EFI_STATUS
DhcpFillOption (
  IN UINT8  Tag,
  IN UINT8  Len,
  IN UINT8  *Data,
  IN VOID   *Context
  )
{
  DHCP_OPTION_CONTEXT  *OptContext;
  DHCP_OPTION_COUNT    *OptCount;
  DHCP_OPTION          *Options;
  UINT8                *Buf;
  UINT8                Index;

  OptContext = (DHCP_OPTION_CONTEXT *)Context;

  OptCount = OptContext->OpCount;
  Index    = OptCount[Tag].Index;
  Options  = OptContext->Options;
  Buf      = OptContext->Buf;

  if (Options[Index].Data == NULL) {
    Options[Index].Tag  = Tag;
    Options[Index].Data = Buf + OptCount[Tag].Offset;
  }

  CopyMem (Buf + OptCount[Tag].Offset, Data, Len);

  OptCount[Tag].Offset = (UINT16)(OptCount[Tag].Offset + Len);
  Options[Index].Len   = (UINT16)(Options[Index].Len + Len);
  return EFI_SUCCESS;
}

/**
  Parse the options of a DHCP packet. It supports RFC 3396: Encoding
  Long Options in DHCP. That is, it will combine all the option value
  of all the occurrences of each option.
  A little bit of implementation:
  It adopts the "Key indexed counting" algorithm. First, it allocates
  an array of 256 DHCP_OPTION_COUNTs because DHCP option tag is encoded
  as a UINT8. It then iterates the DHCP packet to get data length of
  each option by calling DhcpIterOptions with DhcpGetOptionLen. Now, it
  knows the number of present options and their length. It allocates a
  array of DHCP_OPTION and a continuous buffer after the array to put
  all the options' data. Each option's data is pointed to by the Data
  field in DHCP_OPTION structure. At last, it call DhcpIterateOptions
  with DhcpFillOption to fill each option's data to its position in the
  buffer.

  @param[in]  Packet                 The DHCP packet to parse the options
  @param[out] Count                  The number of valid dhcp options present in the
                                     packet
  @param[out] OptionPoint            The array that contains the DHCP options. Caller
                                     should free it.

  @retval EFI_NOT_FOUND          Cannot find any option.
  @retval EFI_OUT_OF_RESOURCES   Failed to allocate memory to parse the packet.
  @retval EFI_INVALID_PARAMETER  The options are mal-formatted
  @retval EFI_SUCCESS            The options are parsed into OptionPoint

**/
EFI_STATUS
DhcpParseOption (
  IN  EFI_DHCP4_PACKET  *Packet,
  OUT INTN              *Count,
  OUT DHCP_OPTION       **OptionPoint
  )
{
  DHCP_OPTION_CONTEXT  Context;
  DHCP_OPTION          *Options;
  DHCP_OPTION_COUNT    *OptCount;
  EFI_STATUS           Status;
  UINT16               TotalLen;
  INTN                 OptNum;
  INTN                 Index;

  ASSERT ((Count != NULL) && (OptionPoint != NULL));

  //
  // First compute how many options and how long each option is
  // with the "Key indexed counting" algorithms.
  //
  OptCount = AllocateZeroPool (DHCP_MAX_OPTIONS * sizeof (DHCP_OPTION_COUNT));

  if (OptCount == NULL) {
    return EFI_OUT_OF_RESOURCES;
  }

  Status = DhcpIterateOptions (Packet, DhcpGetOptionLen, OptCount);

  if (EFI_ERROR (Status)) {
    goto ON_EXIT;
  }

  //
  // Before the loop, Offset is the length of the option. After loop,
  // OptCount[Index].Offset specifies the offset into the continuous
  // option value buffer to put the data.
  //
  TotalLen = 0;
  OptNum   = 0;

  for (Index = 0; Index < DHCP_MAX_OPTIONS; Index++) {
    if (OptCount[Index].Offset != 0) {
      OptCount[Index].Index = (UINT8)OptNum;

      TotalLen               = (UINT16)(TotalLen + OptCount[Index].Offset);
      OptCount[Index].Offset = (UINT16)(TotalLen - OptCount[Index].Offset);

      OptNum++;
    }
  }

  *Count       = OptNum;
  *OptionPoint = NULL;

  if (OptNum == 0) {
    goto ON_EXIT;
  }

  //
  // Allocate a buffer to hold the DHCP options, and after that, a
  // continuous buffer to put all the options' data.
  //
  Options = AllocateZeroPool ((UINTN)(OptNum * sizeof (DHCP_OPTION)) + TotalLen);

  if (Options == NULL) {
    Status = EFI_OUT_OF_RESOURCES;
    goto ON_EXIT;
  }

  Context.OpCount = OptCount;
  Context.Options = Options;
  Context.Buf     = (UINT8 *)(Options + OptNum);

  Status = DhcpIterateOptions (Packet, DhcpFillOption, &Context);

  if (EFI_ERROR (Status)) {
    FreePool (Options);
    goto ON_EXIT;
  }

  *OptionPoint = Options;

ON_EXIT:
  FreePool (OptCount);
  return Status;
}

/**
  Validate the packet's options. If necessary, allocate
  and fill in the interested parameters.

  @param[in]  Packet                 The packet to validate the options
  @param[out] Para                   The variable to save the DHCP parameters.

  @retval EFI_OUT_OF_RESOURCES   Failed to allocate memory to validate the packet.
  @retval EFI_INVALID_PARAMETER  The options are mal-formatted
  @retval EFI_SUCCESS            The options are parsed into OptionPoint

**/
EFI_STATUS
DhcpValidateOptions (
  IN  EFI_DHCP4_PACKET  *Packet,
  OUT DHCP_PARAMETER    **Para       OPTIONAL
  )
{
  DHCP_PARAMETER      Parameter;
  DHCP_OPTION_FORMAT  *Format;
  DHCP_OPTION         *AllOption;
  DHCP_OPTION         *Option;
  EFI_STATUS          Status;
  BOOLEAN             Updated;
  INTN                Count;
  INTN                Index;

  if (Para != NULL) {
    *Para = NULL;
  }

  AllOption = NULL;

  Status = DhcpParseOption (Packet, &Count, &AllOption);
  if (EFI_ERROR (Status) || (Count == 0)) {
    return Status;
  }

  ASSERT (AllOption != NULL);

  Updated = FALSE;
  ZeroMem (&Parameter, sizeof (Parameter));

  for (Index = 0; Index < Count; Index++) {
    Option = &AllOption[Index];

    //
    // Find the format of the option then validate it.
    //
    Format = DhcpFindOptionFormat (Option->Tag);

    if (Format == NULL) {
      continue;
    }

    if (!DhcpOptionIsValid (Format, Option->Data, Option->Len)) {
      Status = EFI_INVALID_PARAMETER;
      goto ON_EXIT;
    }

    //
    // Get the client interested parameters
    //
    if (Format->Alert && (Para != NULL)) {
      Updated = TRUE;
      Status  = DhcpGetParameter (Option->Tag, Option->Len, Option->Data, &Parameter);

      if (EFI_ERROR (Status)) {
        goto ON_EXIT;
      }
    }
  }

  if (Updated && (Para != NULL)) {
    *Para = AllocateCopyPool (sizeof (DHCP_PARAMETER), &Parameter);
    if (*Para == NULL) {
      Status = EFI_OUT_OF_RESOURCES;
      goto ON_EXIT;
    }
  }

ON_EXIT:
  FreePool (AllOption);
  return Status;
}

/**
  Append an option to the memory, if the option is longer than
  255 bytes, splits it into several options.

  @param[out] Buf                    The buffer to append the option to
  @param[in]  Tag                    The option's tag
  @param[in]  DataLen                The length of the option's data
  @param[in]  Data                   The option's data

  @return The position to append the next option

**/
UINT8 *
DhcpAppendOption (
  OUT UINT8   *Buf,
  IN  UINT8   Tag,
  IN  UINT16  DataLen,
  IN  UINT8   *Data
  )
{
  INTN  Index;
  INTN  Len;

  ASSERT (DataLen != 0);

  for (Index = 0; Index < (DataLen + 254) / 255; Index++) {
    Len = MIN (255, DataLen - Index * 255);

    *(Buf++) = Tag;
    *(Buf++) = (UINT8)Len;
    CopyMem (Buf, Data + Index * 255, (UINTN)Len);

    Buf += Len;
  }

  return Buf;
}

/**
  Build a new DHCP packet from a seed packet. Options may be deleted or
  appended. The caller should free the NewPacket when finished using it.

  @param[in]  SeedPacket             The seed packet to start with
  @param[in]  DeleteCount            The number of options to delete
  @param[in]  DeleteList             The options to delete from the packet
  @param[in]  AppendCount            The number of options to append
  @param[in]  AppendList             The options to append to the packet
  @param[out] NewPacket              The new packet, allocated and built by this
                                     function.

  @retval EFI_OUT_OF_RESOURCES   Failed to allocate memory
  @retval EFI_INVALID_PARAMETER  The options in SeekPacket are mal-formatted
  @retval EFI_SUCCESS            The packet is build.

**/
EFI_STATUS
DhcpBuild (
  IN  EFI_DHCP4_PACKET         *SeedPacket,
  IN  UINT32                   DeleteCount,
  IN  UINT8                    *DeleteList     OPTIONAL,
  IN  UINT32                   AppendCount,
  IN  EFI_DHCP4_PACKET_OPTION  *AppendList[]   OPTIONAL,
  OUT EFI_DHCP4_PACKET         **NewPacket
  )
{
  DHCP_OPTION       *Mark;
  DHCP_OPTION       *SeedOptions;
  EFI_DHCP4_PACKET  *Packet;
  EFI_STATUS        Status;
  INTN              Count;
  UINT32            Index;
  UINT32            Len;
  UINT8             *Buf;

  //
  // Use an array of DHCP_OPTION to mark the existence
  // and position of each valid options.
  //
  Mark = AllocatePool (sizeof (DHCP_OPTION) * DHCP_MAX_OPTIONS);

  if (Mark == NULL) {
    return EFI_OUT_OF_RESOURCES;
  }

  for (Index = 0; Index < DHCP_MAX_OPTIONS; Index++) {
    Mark[Index].Tag = (UINT8)Index;
    Mark[Index].Len = 0;
  }

  //
  // Get list of the options from the seed packet, then put
  // them to the mark array according to their tags.
  //
  SeedOptions = NULL;
  Status      = DhcpParseOption (SeedPacket, &Count, &SeedOptions);

  if (EFI_ERROR (Status)) {
    goto ON_ERROR;
  }

  if (SeedOptions != NULL) {
    for (Index = 0; Index < (UINT32)Count; Index++) {
      Mark[SeedOptions[Index].Tag] = SeedOptions[Index];
    }
  }

  //
  // Mark the option's length is zero if it is in the DeleteList.
  //
  for (Index = 0; Index < DeleteCount; Index++) {
    Mark[DeleteList[Index]].Len = 0;
  }

  //
  // Add or replace the option if it is in the append list.
  //
  for (Index = 0; Index < AppendCount; Index++) {
    Mark[AppendList[Index]->OpCode].Len  = AppendList[Index]->Length;
    Mark[AppendList[Index]->OpCode].Data = AppendList[Index]->Data;
  }

  //
  // compute the new packet length. No need to add 1 byte for
  // EOP option since EFI_DHCP4_PACKET includes one extra byte
  // for option. It is necessary to split the option if it is
  // longer than 255 bytes.
  //
  Len = sizeof (EFI_DHCP4_PACKET);

  for (Index = 0; Index < DHCP_MAX_OPTIONS; Index++) {
    if (Mark[Index].Len != 0) {
      Len += ((Mark[Index].Len + 254) / 255) * 2 + Mark[Index].Len;
    }
  }

  Status = EFI_OUT_OF_RESOURCES;
  Packet = (EFI_DHCP4_PACKET *)AllocatePool (Len);

  if (Packet == NULL) {
    goto ON_ERROR;
  }

  Packet->Size   = Len;
  Packet->Length = 0;
  CopyMem (&Packet->Dhcp4.Header, &SeedPacket->Dhcp4.Header, sizeof (Packet->Dhcp4.Header));
  Packet->Dhcp4.Magik = DHCP_OPTION_MAGIC;
  Buf                 = Packet->Dhcp4.Option;

  for (Index = 0; Index < DHCP_MAX_OPTIONS; Index++) {
    if (Mark[Index].Len != 0) {
      Buf = DhcpAppendOption (Buf, Mark[Index].Tag, Mark[Index].Len, Mark[Index].Data);
    }
  }

  *(Buf++)       = DHCP4_TAG_EOP;
  Packet->Length = sizeof (EFI_DHCP4_HEADER) + sizeof (UINT32)
                   + (UINT32)(Buf - Packet->Dhcp4.Option);

  *NewPacket = Packet;
  Status     = EFI_SUCCESS;

ON_ERROR:
  if (SeedOptions != NULL) {
    FreePool (SeedOptions);
  }

  FreePool (Mark);
  return Status;
}
