// Copyright 2014 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com

#include "xfa/fxfa/fm2js/cxfa_fmparser.h"

#include <memory>
#include <utility>
#include <vector>

#include "core/fxcrt/autorestorer.h"
#include "third_party/base/ptr_util.h"

namespace {

constexpr unsigned int kMaxParseDepth = 1250;
constexpr unsigned int kMaxPostExpressions = 16384;

}  // namespace

CXFA_FMParser::CXFA_FMParser(const WideStringView& wsFormcalc)
    : m_error(false), m_parse_depth(0), m_max_parse_depth(kMaxParseDepth) {
  m_lexer = pdfium::MakeUnique<CXFA_FMLexer>(wsFormcalc);
  m_token = m_lexer->NextToken();
}

CXFA_FMParser::~CXFA_FMParser() {}

std::unique_ptr<CXFA_FMFunctionDefinition> CXFA_FMParser::Parse() {
  auto expressions = ParseExpressionList();
  if (HasError())
    return nullptr;

  std::vector<WideStringView> arguments;
  return pdfium::MakeUnique<CXFA_FMFunctionDefinition>(
      true, L"", std::move(arguments), std::move(expressions));
}

bool CXFA_FMParser::NextToken() {
  if (HasError())
    return false;

  m_token = m_lexer->NextToken();
  while (!HasError() && m_token.m_type == TOKreserver)
    m_token = m_lexer->NextToken();
  return !HasError();
}

bool CXFA_FMParser::CheckThenNext(XFA_FM_TOKEN op) {
  if (HasError())
    return false;

  if (m_token.m_type != op) {
    m_error = true;
    return false;
  }
  return NextToken();
}

bool CXFA_FMParser::IncrementParseDepthAndCheck() {
  return ++m_parse_depth < m_max_parse_depth;
}

std::vector<std::unique_ptr<CXFA_FMExpression>>
CXFA_FMParser::ParseExpressionList() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return std::vector<std::unique_ptr<CXFA_FMExpression>>();
  std::vector<std::unique_ptr<CXFA_FMExpression>> expressions;
  while (!HasError()) {
    if (m_token.m_type == TOKeof || m_token.m_type == TOKendfunc ||
        m_token.m_type == TOKendif || m_token.m_type == TOKelseif ||
        m_token.m_type == TOKelse || m_token.m_type == TOKendwhile ||
        m_token.m_type == TOKendfor || m_token.m_type == TOKend ||
        m_token.m_type == TOKendfunc || m_token.m_type == TOKreserver) {
      break;
    }

    std::unique_ptr<CXFA_FMExpression> expr =
        m_token.m_type == TOKfunc ? ParseFunction() : ParseExpression();
    if (!expr) {
      m_error = true;
      return std::vector<std::unique_ptr<CXFA_FMExpression>>();
    }
    expressions.push_back(std::move(expr));
  }
  return expressions;
}

std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseFunction() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  WideStringView ident;
  std::vector<WideStringView> arguments;
  std::vector<std::unique_ptr<CXFA_FMExpression>> expressions;
  if (!NextToken())
    return nullptr;
  if (m_token.m_type != TOKidentifier) {
    m_error = true;
    return nullptr;
  } else {
    ident = m_token.m_string;
    if (!NextToken())
      return nullptr;
  }
  if (!CheckThenNext(TOKlparen))
    return nullptr;
  if (m_token.m_type == TOKrparen) {
    if (!NextToken())
      return nullptr;
  } else {
    while (1) {
      if (m_token.m_type != TOKidentifier) {
        m_error = true;
        return nullptr;
      }
      arguments.push_back(m_token.m_string);
      if (!NextToken())
        return nullptr;
      if (m_token.m_type == TOKcomma) {
        if (!NextToken())
          return nullptr;
        continue;
      }
      if (m_token.m_type == TOKrparen) {
        if (!NextToken())
          return nullptr;
      } else {
        if (!CheckThenNext(TOKrparen))
          return nullptr;
      }
      break;
    }
  }
  if (!CheckThenNext(TOKdo))
    return nullptr;
  if (m_token.m_type == TOKendfunc) {
    if (!NextToken())
      return nullptr;
  } else {
    expressions = ParseExpressionList();
    if (!expressions.size() || !CheckThenNext(TOKendfunc))
      return nullptr;
  }

  return pdfium::MakeUnique<CXFA_FMFunctionDefinition>(
      false, ident, std::move(arguments), std::move(expressions));
}

std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMExpression> expr;
  switch (m_token.m_type) {
    case TOKvar:
      expr = ParseDeclarationExpression();
      break;
    case TOKnull:
    case TOKnumber:
    case TOKstring:
    case TOKplus:
    case TOKminus:
    case TOKksnot:
    case TOKidentifier:
    case TOKlparen:
      expr = ParseExpExpression();
      break;
    case TOKif:
      expr = ParseIfExpression();
      break;
    case TOKwhile:
      expr = ParseWhileExpression();
      break;
    case TOKfor:
      expr = ParseForExpression();
      break;
    case TOKforeach:
      expr = ParseForeachExpression();
      break;
    case TOKdo:
      expr = ParseDoExpression();
      break;
    case TOKbreak:
      expr = pdfium::MakeUnique<CXFA_FMBreakExpression>();
      if (!NextToken())
        return nullptr;
      break;
    case TOKcontinue:
      expr = pdfium::MakeUnique<CXFA_FMContinueExpression>();
      if (!NextToken())
        return nullptr;
      break;
    default:
      m_error = true;
      return nullptr;
  }
  return expr;
}

std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseDeclarationExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  WideStringView ident;
  if (!NextToken())
    return nullptr;
  if (m_token.m_type != TOKidentifier) {
    m_error = true;
    return nullptr;
  }

  ident = m_token.m_string;
  if (!NextToken())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> expr;
  if (m_token.m_type == TOKassign) {
    if (!NextToken())
      return nullptr;

    expr = ParseSimpleExpression();
    if (!expr)
      return nullptr;
  }

  return pdfium::MakeUnique<CXFA_FMVarExpression>(ident, std::move(expr));
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseSimpleExpression() {
  if (HasError())
    return nullptr;

  return ParseLogicalOrExpression();
}

std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseExpExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> pExp1 = ParseSimpleExpression();
  if (!pExp1)
    return nullptr;

  if (m_token.m_type == TOKassign) {
    if (!NextToken())
      return nullptr;

    std::unique_ptr<CXFA_FMSimpleExpression> pExp2 = ParseSimpleExpression();
    if (!pExp2)
      return nullptr;

    pExp1 = pdfium::MakeUnique<CXFA_FMAssignExpression>(
        TOKassign, std::move(pExp1), std::move(pExp2));
  }
  return pdfium::MakeUnique<CXFA_FMExpExpression>(std::move(pExp1));
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseLogicalOrExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> e1 = ParseLogicalAndExpression();
  if (!e1)
    return nullptr;

  for (;;) {
    switch (m_token.m_type) {
      case TOKor:
      case TOKksor: {
        if (!NextToken())
          return nullptr;

        std::unique_ptr<CXFA_FMSimpleExpression> e2(
            ParseLogicalAndExpression());
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMLogicalOrExpression>(
            TOKor, std::move(e1), std::move(e2));
        continue;
      }
      default:
        break;
    }
    break;
  }
  return e1;
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseLogicalAndExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> e1 = ParseEqualityExpression();
  if (!e1)
    return nullptr;

  for (;;) {
    switch (m_token.m_type) {
      case TOKand:
      case TOKksand: {
        if (!NextToken())
          return nullptr;

        std::unique_ptr<CXFA_FMSimpleExpression> e2 = ParseEqualityExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMLogicalAndExpression>(
            TOKand, std::move(e1), std::move(e2));
        continue;
      }
      default:
        break;
    }
    break;
  }
  return e1;
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseEqualityExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> e1 = ParseRelationalExpression();
  if (!e1)
    return nullptr;
  for (;;) {
    std::unique_ptr<CXFA_FMSimpleExpression> e2;
    switch (m_token.m_type) {
      case TOKeq:
      case TOKkseq:
        if (!NextToken())
          return nullptr;

        e2 = ParseRelationalExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMEqualExpression>(TOKeq, std::move(e1),
                                                        std::move(e2));
        continue;
      case TOKne:
      case TOKksne:
        if (!NextToken())
          return nullptr;

        e2 = ParseRelationalExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMNotEqualExpression>(TOKne, std::move(e1),
                                                           std::move(e2));
        continue;
      default:
        break;
    }
    break;
  }
  return e1;
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseRelationalExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> e1 = ParseAddtiveExpression();
  if (!e1)
    return nullptr;

  for (;;) {
    std::unique_ptr<CXFA_FMSimpleExpression> e2;
    switch (m_token.m_type) {
      case TOKlt:
      case TOKkslt:
        if (!NextToken())
          return nullptr;

        e2 = ParseAddtiveExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMLtExpression>(TOKlt, std::move(e1),
                                                     std::move(e2));
        continue;
      case TOKgt:
      case TOKksgt:
        if (!NextToken())
          return nullptr;

        e2 = ParseAddtiveExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMGtExpression>(TOKgt, std::move(e1),
                                                     std::move(e2));
        continue;
      case TOKle:
      case TOKksle:
        if (!NextToken())
          return nullptr;

        e2 = ParseAddtiveExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMLeExpression>(TOKle, std::move(e1),
                                                     std::move(e2));
        continue;
      case TOKge:
      case TOKksge:
        if (!NextToken())
          return nullptr;

        e2 = ParseAddtiveExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMGeExpression>(TOKge, std::move(e1),
                                                     std::move(e2));
        continue;
      default:
        break;
    }
    break;
  }
  return e1;
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseAddtiveExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> e1 = ParseMultiplicativeExpression();
  if (!e1)
    return nullptr;

  for (;;) {
    std::unique_ptr<CXFA_FMSimpleExpression> e2;
    switch (m_token.m_type) {
      case TOKplus:
        if (!NextToken())
          return nullptr;

        e2 = ParseMultiplicativeExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMPlusExpression>(TOKplus, std::move(e1),
                                                       std::move(e2));
        continue;
      case TOKminus:
        if (!NextToken())
          return nullptr;

        e2 = ParseMultiplicativeExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMMinusExpression>(TOKminus, std::move(e1),
                                                        std::move(e2));
        continue;
      default:
        break;
    }
    break;
  }
  return e1;
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseMultiplicativeExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> e1 = ParseUnaryExpression();
  if (!e1)
    return nullptr;

  for (;;) {
    std::unique_ptr<CXFA_FMSimpleExpression> e2;
    switch (m_token.m_type) {
      case TOKmul:
        if (!NextToken())
          return nullptr;

        e2 = ParseUnaryExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMMulExpression>(TOKmul, std::move(e1),
                                                      std::move(e2));
        continue;
      case TOKdiv:
        if (!NextToken())
          return nullptr;

        e2 = ParseUnaryExpression();
        if (!e2)
          return nullptr;

        e1 = pdfium::MakeUnique<CXFA_FMDivExpression>(TOKdiv, std::move(e1),
                                                      std::move(e2));
        continue;
      default:
        break;
    }
    break;
  }
  return e1;
}

std::unique_ptr<CXFA_FMSimpleExpression> CXFA_FMParser::ParseUnaryExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> expr;
  switch (m_token.m_type) {
    case TOKplus:
      if (!NextToken())
        return nullptr;

      expr = ParseUnaryExpression();
      if (!expr)
        return nullptr;

      expr = pdfium::MakeUnique<CXFA_FMPosExpression>(std::move(expr));
      break;
    case TOKminus:
      if (!NextToken())
        return nullptr;

      expr = ParseUnaryExpression();
      if (!expr)
        return nullptr;

      expr = pdfium::MakeUnique<CXFA_FMNegExpression>(std::move(expr));
      break;
    case TOKksnot:
      if (!NextToken())
        return nullptr;

      expr = ParseUnaryExpression();
      if (!expr)
        return nullptr;

      expr = pdfium::MakeUnique<CXFA_FMNotExpression>(std::move(expr));
      break;
    default:
      expr = ParsePrimaryExpression();
      if (!expr)
        return nullptr;
      break;
  }
  return expr;
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParsePrimaryExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> expr = ParseLiteral();
  if (expr)
    return NextToken() ? std::move(expr) : nullptr;

  switch (m_token.m_type) {
    case TOKidentifier: {
      WideStringView wsIdentifier(m_token.m_string);
      if (!NextToken())
        return nullptr;
      if (m_token.m_type == TOKlbracket) {
        std::unique_ptr<CXFA_FMSimpleExpression> s = ParseIndexExpression();
        if (!s)
          return nullptr;

        expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
            nullptr, TOKdot, wsIdentifier, std::move(s));
        if (!expr)
          return nullptr;
        if (!NextToken())
          return nullptr;
      } else {
        expr = pdfium::MakeUnique<CXFA_FMIdentifierExpression>(wsIdentifier);
      }
      break;
    }
    case TOKlparen:
      expr = ParseParenExpression();
      if (!expr)
        return nullptr;
      break;
    default:
      m_error = true;
      return nullptr;
  }
  expr = ParsePostExpression(std::move(expr));
  if (!expr)
    return nullptr;
  return expr;
}

// Literal := String | Number | Null
std::unique_ptr<CXFA_FMSimpleExpression> CXFA_FMParser::ParseLiteral() {
  switch (m_token.m_type) {
    case TOKnumber:
      return pdfium::MakeUnique<CXFA_FMNumberExpression>(m_token.m_string);
    case TOKstring:
      return pdfium::MakeUnique<CXFA_FMStringExpression>(m_token.m_string);
    case TOKnull:
      return pdfium::MakeUnique<CXFA_FMNullExpression>();
    default:
      return nullptr;
  }
}

std::unique_ptr<CXFA_FMSimpleExpression> CXFA_FMParser::ParsePostExpression(
    std::unique_ptr<CXFA_FMSimpleExpression> expr) {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  size_t expr_count = 0;
  while (1) {
    ++expr_count;
    // Limit the number of expressions allowed in the post expression statement.
    // If we don't do this then its possible to generate a stack overflow
    // by having a very large number of things like .. expressions.
    if (expr_count > kMaxPostExpressions)
      return nullptr;

    switch (m_token.m_type) {
      case TOKlparen: {
        if (!NextToken())
          return nullptr;
        std::vector<std::unique_ptr<CXFA_FMSimpleExpression>> expressions;
        if (m_token.m_type != TOKrparen) {
          while (m_token.m_type != TOKrparen) {
            std::unique_ptr<CXFA_FMSimpleExpression> simple_expr =
                ParseSimpleExpression();
            if (!simple_expr)
              return nullptr;

            expressions.push_back(std::move(simple_expr));
            if (m_token.m_type == TOKcomma) {
              if (!NextToken())
                return nullptr;
            } else if (m_token.m_type == TOKeof ||
                       m_token.m_type == TOKreserver) {
              break;
            }
          }
          if (m_token.m_type != TOKrparen) {
            m_error = true;
            return nullptr;
          }
        }
        expr = pdfium::MakeUnique<CXFA_FMCallExpression>(
            std::move(expr), std::move(expressions), false);
        if (!NextToken())
          return nullptr;
        if (m_token.m_type != TOKlbracket)
          continue;

        std::unique_ptr<CXFA_FMSimpleExpression> s = ParseIndexExpression();
        if (!s)
          return nullptr;

        expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
            std::move(expr), TOKcall, L"", std::move(s));
        break;
      }
      case TOKdot: {
        if (!NextToken())
          return nullptr;
        if (m_token.m_type != TOKidentifier) {
          m_error = true;
          return nullptr;
        }
        WideStringView tempStr = m_token.m_string;
        if (!NextToken())
          return nullptr;
        if (m_token.m_type == TOKlparen) {
          std::unique_ptr<CXFA_FMSimpleExpression> pExpCall;
          if (!NextToken())
            return nullptr;

          std::vector<std::unique_ptr<CXFA_FMSimpleExpression>> expressions;
          if (m_token.m_type != TOKrparen) {
            while (m_token.m_type != TOKrparen) {
              std::unique_ptr<CXFA_FMSimpleExpression> exp =
                  ParseSimpleExpression();
              if (!exp)
                return nullptr;

              expressions.push_back(std::move(exp));
              if (m_token.m_type == TOKcomma) {
                if (!NextToken())
                  return nullptr;
              } else if (m_token.m_type == TOKeof ||
                         m_token.m_type == TOKreserver) {
                break;
              }
            }
            if (m_token.m_type != TOKrparen) {
              m_error = true;
              return nullptr;
            }
          }
          std::unique_ptr<CXFA_FMSimpleExpression> pIdentifier =
              pdfium::MakeUnique<CXFA_FMIdentifierExpression>(tempStr);
          pExpCall = pdfium::MakeUnique<CXFA_FMCallExpression>(
              std::move(pIdentifier), std::move(expressions), true);
          expr = pdfium::MakeUnique<CXFA_FMMethodCallExpression>(
              std::move(expr), std::move(pExpCall));
          if (!NextToken())
            return nullptr;
          if (m_token.m_type != TOKlbracket)
            continue;

          std::unique_ptr<CXFA_FMSimpleExpression> s = ParseIndexExpression();
          if (!s)
            return nullptr;

          expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
              std::move(expr), TOKcall, L"", std::move(s));
        } else if (m_token.m_type == TOKlbracket) {
          std::unique_ptr<CXFA_FMSimpleExpression> s = ParseIndexExpression();
          if (!s)
            return nullptr;

          expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
              std::move(expr), TOKdot, tempStr, std::move(s));
        } else {
          std::unique_ptr<CXFA_FMSimpleExpression> s =
              pdfium::MakeUnique<CXFA_FMIndexExpression>(ACCESSOR_NO_INDEX,
                                                         nullptr, false);
          expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
              std::move(expr), TOKdot, tempStr, std::move(s));
          continue;
        }
      } break;
      case TOKdotdot: {
        if (!NextToken())
          return nullptr;
        if (m_token.m_type != TOKidentifier) {
          m_error = true;
          return nullptr;
        }

        WideStringView tempStr = m_token.m_string;
        if (!NextToken())
          return nullptr;
        if (m_token.m_type == TOKlbracket) {
          std::unique_ptr<CXFA_FMSimpleExpression> s = ParseIndexExpression();
          if (!s)
            return nullptr;

          expr = pdfium::MakeUnique<CXFA_FMDotDotAccessorExpression>(
              std::move(expr), TOKdotdot, tempStr, std::move(s));
        } else {
          std::unique_ptr<CXFA_FMSimpleExpression> s =
              pdfium::MakeUnique<CXFA_FMIndexExpression>(ACCESSOR_NO_INDEX,
                                                         nullptr, false);
          expr = pdfium::MakeUnique<CXFA_FMDotDotAccessorExpression>(
              std::move(expr), TOKdotdot, tempStr, std::move(s));
          continue;
        }
      } break;
      case TOKdotscream: {
        if (!NextToken())
          return nullptr;
        if (m_token.m_type != TOKidentifier) {
          m_error = true;
          return nullptr;
        }

        WideStringView tempStr = m_token.m_string;
        if (!NextToken())
          return nullptr;
        if (m_token.m_type != TOKlbracket) {
          std::unique_ptr<CXFA_FMSimpleExpression> s =
              pdfium::MakeUnique<CXFA_FMIndexExpression>(ACCESSOR_NO_INDEX,
                                                         nullptr, false);
          expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
              std::move(expr), TOKdotscream, tempStr, std::move(s));
          continue;
        }
        std::unique_ptr<CXFA_FMSimpleExpression> s = ParseIndexExpression();
        if (!s)
          return nullptr;

        expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
            std::move(expr), TOKdotscream, tempStr, std::move(s));
        break;
      }
      case TOKdotstar: {
        std::unique_ptr<CXFA_FMSimpleExpression> s =
            pdfium::MakeUnique<CXFA_FMIndexExpression>(ACCESSOR_NO_INDEX,
                                                       nullptr, false);
        expr = pdfium::MakeUnique<CXFA_FMDotAccessorExpression>(
            std::move(expr), TOKdotstar, L"*", std::move(s));
        break;
      }
      default:
        return expr;
    }
    if (!NextToken())
      return nullptr;
  }
  return expr;
}

std::unique_ptr<CXFA_FMSimpleExpression> CXFA_FMParser::ParseIndexExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;
  if (!NextToken())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> s;
  XFA_FM_AccessorIndex accessorIndex = ACCESSOR_NO_RELATIVEINDEX;
  std::unique_ptr<CXFA_FMSimpleExpression> pExp;
  if (m_token.m_type == TOKmul) {
    pExp = pdfium::MakeUnique<CXFA_FMIndexExpression>(accessorIndex,
                                                      std::move(s), true);
    if (!pExp || !NextToken())
      return nullptr;
    if (m_token.m_type != TOKrbracket) {
      m_error = true;
      return nullptr;
    }
    return pExp;
  }
  if (m_token.m_type == TOKplus) {
    accessorIndex = ACCESSOR_POSITIVE_INDEX;
    if (!NextToken())
      return nullptr;
  } else if (m_token.m_type == TOKminus) {
    accessorIndex = ACCESSOR_NEGATIVE_INDEX;
    if (!NextToken())
      return nullptr;
  }
  s = ParseSimpleExpression();
  if (!s)
    return nullptr;
  if (m_token.m_type != TOKrbracket) {
    m_error = true;
    return nullptr;
  }
  return pdfium::MakeUnique<CXFA_FMIndexExpression>(accessorIndex, std::move(s),
                                                    false);
}

std::unique_ptr<CXFA_FMSimpleExpression> CXFA_FMParser::ParseParenExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  if (!CheckThenNext(TOKlparen))
    return nullptr;

  if (m_token.m_type == TOKrparen) {
    m_error = true;
    return nullptr;
  }

  std::unique_ptr<CXFA_FMSimpleExpression> pExp1 = ParseSimpleExpression();
  if (!pExp1)
    return nullptr;

  if (!CheckThenNext(TOKrparen))
    return nullptr;
  return pExp1;
}

std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseIfExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;
  if (!NextToken() || !CheckThenNext(TOKlparen))
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> pExpression;
  while (m_token.m_type != TOKrparen) {
    pExpression = ParseSimpleExpression();
    if (!pExpression)
      return nullptr;
    if (m_token.m_type != TOKcomma)
      break;
    if (!NextToken())
      return nullptr;
  }
  if (!CheckThenNext(TOKrparen))
    return nullptr;

  if (m_token.m_type != TOKthen) {
    m_error = true;
    return nullptr;
  }
  if (!NextToken())
    return nullptr;

  auto exprs = ParseExpressionList();
  if (exprs.empty()) {
    m_error = true;
    return nullptr;
  }
  if (m_token.m_type != TOKelseif && m_token.m_type != TOKelse &&
      m_token.m_type != TOKendif) {
    m_error = true;
    return nullptr;
  }
  auto pIfExpression =
      pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(exprs));

  std::unique_ptr<CXFA_FMExpression> pElseExpression;
  switch (m_token.m_type) {
    case TOKeof:
    case TOKendif:
      if (!CheckThenNext(TOKendif))
        return nullptr;
      break;
    case TOKif:
      pElseExpression = ParseIfExpression();
      if (!pElseExpression || !CheckThenNext(TOKendif)) {
        m_error = true;
        return nullptr;
      }
      break;
    case TOKelseif:
      pElseExpression = ParseIfExpression();
      if (!pElseExpression) {
        m_error = true;
        return nullptr;
      }
      break;
    case TOKelse: {
      if (!NextToken())
        return nullptr;

      auto else_exprs = ParseExpressionList();
      if (else_exprs.empty() || !CheckThenNext(TOKendif)) {
        m_error = true;
        return nullptr;
      }

      pElseExpression =
          pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(else_exprs));
      break;
    }
    default:
      m_error = true;
      return nullptr;
  }
  return pdfium::MakeUnique<CXFA_FMIfExpression>(std::move(pExpression),
                                                 std::move(pIfExpression),
                                                 std::move(pElseExpression));
}

std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseWhileExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;
  if (!NextToken())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> pCondition = ParseParenExpression();
  if (!pCondition || !CheckThenNext(TOKdo))
    return nullptr;

  auto exprs = ParseExpressionList();
  if (exprs.empty() || !CheckThenNext(TOKendwhile)) {
    m_error = true;
    return nullptr;
  }
  return pdfium::MakeUnique<CXFA_FMWhileExpression>(
      std::move(pCondition),
      pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(exprs)));
}

std::unique_ptr<CXFA_FMSimpleExpression>
CXFA_FMParser::ParseSubassignmentInForExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  if (m_token.m_type != TOKidentifier) {
    m_error = true;
    return nullptr;
  }
  std::unique_ptr<CXFA_FMSimpleExpression> expr = ParseSimpleExpression();
  if (!expr)
    return nullptr;
  return expr;
}

std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseForExpression() {
  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;

  WideStringView wsVariant;
  if (!NextToken())
    return nullptr;
  if (m_token.m_type != TOKidentifier) {
    m_error = true;
    return nullptr;
  }

  wsVariant = m_token.m_string;
  if (!NextToken())
    return nullptr;
  if (m_token.m_type != TOKassign) {
    m_error = true;
    return nullptr;
  }
  if (!NextToken())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> pAssignment =
      ParseSimpleExpression();
  if (!pAssignment)
    return nullptr;

  int32_t iDirection = 0;
  if (m_token.m_type == TOKupto) {
    iDirection = 1;
  } else if (m_token.m_type == TOKdownto) {
    iDirection = -1;
  } else {
    m_error = true;
    return nullptr;
  }

  if (!NextToken())
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> pAccessor = ParseSimpleExpression();
  if (!pAccessor)
    return nullptr;

  std::unique_ptr<CXFA_FMSimpleExpression> pStep;
  if (m_token.m_type == TOKstep) {
    if (!NextToken())
      return nullptr;
    pStep = ParseSimpleExpression();
    if (!pStep)
      return nullptr;
  }
  if (!CheckThenNext(TOKdo))
    return nullptr;

  auto exprs = ParseExpressionList();
  if (exprs.empty() || !CheckThenNext(TOKendfor)) {
    m_error = true;
    return nullptr;
  }

  return pdfium::MakeUnique<CXFA_FMForExpression>(
      wsVariant, std::move(pAssignment), std::move(pAccessor), iDirection,
      std::move(pStep),
      pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(exprs)));
}

// Foreach := 'foreach' Identifier 'in' '(' ArgumentList ')'
//            'do' ExpressionList 'endfor'
std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseForeachExpression() {
  if (m_token.m_type != TOKforeach)
    return nullptr;

  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;
  if (!NextToken())
    return nullptr;

  if (m_token.m_type != TOKidentifier) {
    m_error = true;
    return nullptr;
  }
  WideStringView wsIdentifier = m_token.m_string;
  if (!NextToken() || !CheckThenNext(TOKin) || !CheckThenNext(TOKlparen))
    return nullptr;

  std::vector<std::unique_ptr<CXFA_FMSimpleExpression>> pArgumentList;
  while (m_token.m_type != TOKrparen) {
    std::unique_ptr<CXFA_FMSimpleExpression> s = ParseSimpleExpression();
    if (!s)
      return nullptr;

    pArgumentList.push_back(std::move(s));
    if (m_token.m_type != TOKcomma)
      break;
    if (!NextToken())
      return nullptr;
  }
  // We must have arguments.
  if (pArgumentList.empty()) {
    m_error = true;
    return nullptr;
  }

  if (!CheckThenNext(TOKrparen))
    return nullptr;

  auto exprs = ParseExpressionList();
  if (exprs.empty() || !CheckThenNext(TOKendfor)) {
    m_error = true;
    return nullptr;
  }

  return pdfium::MakeUnique<CXFA_FMForeachExpression>(
      wsIdentifier, std::move(pArgumentList),
      pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(exprs)));
}

// Block := 'do' ExpressionList 'end'
std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseDoExpression() {
  if (m_token.m_type != TOKdo)
    return nullptr;

  AutoRestorer<unsigned long> restorer(&m_parse_depth);
  if (HasError() || !IncrementParseDepthAndCheck())
    return nullptr;
  if (!NextToken())
    return nullptr;

  auto exprs = ParseExpressionList();
  if (exprs.empty() || !CheckThenNext(TOKend)) {
    m_error = true;
    return nullptr;
  }

  return pdfium::MakeUnique<CXFA_FMDoExpression>(
      pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(exprs)));
}

bool CXFA_FMParser::HasError() const {
  return m_error || m_token.m_type == TOKreserver;
}
