summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--xfa/fxfa/fm2js/cxfa_fmexpression.cpp28
-rw-r--r--xfa/fxfa/fm2js/cxfa_fmexpression.h9
-rw-r--r--xfa/fxfa/fm2js/cxfa_fmparser.cpp89
-rw-r--r--xfa/fxfa/fm2js/cxfa_fmparser_unittest.cpp7
4 files changed, 55 insertions, 78 deletions
diff --git a/xfa/fxfa/fm2js/cxfa_fmexpression.cpp b/xfa/fxfa/fm2js/cxfa_fmexpression.cpp
index a4dee6353b..db93a38e50 100644
--- a/xfa/fxfa/fm2js/cxfa_fmexpression.cpp
+++ b/xfa/fxfa/fm2js/cxfa_fmexpression.cpp
@@ -220,11 +220,15 @@ bool CXFA_FMDoExpression::ToJavaScript(CFX_WideTextBuf& js, ReturnType type) {
CXFA_FMIfExpression::CXFA_FMIfExpression(
std::unique_ptr<CXFA_FMSimpleExpression> pExpression,
std::unique_ptr<CXFA_FMExpression> pIfExpression,
+ std::vector<std::unique_ptr<CXFA_FMIfExpression>> pElseIfExpressions,
std::unique_ptr<CXFA_FMExpression> pElseExpression)
: CXFA_FMExpression(),
m_pExpression(std::move(pExpression)),
m_pIfExpression(std::move(pIfExpression)),
- m_pElseExpression(std::move(pElseExpression)) {}
+ m_pElseIfExpressions(std::move(pElseIfExpressions)),
+ m_pElseExpression(std::move(pElseExpression)) {
+ ASSERT(m_pExpression);
+}
CXFA_FMIfExpression::~CXFA_FMIfExpression() = default;
@@ -236,15 +240,10 @@ bool CXFA_FMIfExpression::ToJavaScript(CFX_WideTextBuf& js, ReturnType type) {
if (type == ReturnType::kImplied)
js << L"pfm_ret = 0;\n";
- js << L"if (";
- if (m_pExpression) {
- js << L"pfm_rt.get_val(";
- if (!m_pExpression->ToJavaScript(js, ReturnType::kInfered))
- return false;
-
- js << L")";
- }
- js << L")\n";
+ js << L"if (pfm_rt.get_val(";
+ if (!m_pExpression->ToJavaScript(js, ReturnType::kInfered))
+ return false;
+ js << L"))\n";
if (CXFA_IsTooBig(js))
return false;
@@ -256,11 +255,16 @@ bool CXFA_FMIfExpression::ToJavaScript(CFX_WideTextBuf& js, ReturnType type) {
return false;
}
+ for (auto& expr : m_pElseIfExpressions) {
+ js << L"else ";
+ if (!expr->ToJavaScript(js, ReturnType::kInfered))
+ return false;
+ }
+
if (m_pElseExpression) {
- js << L"else\n{\n";
+ js << L"else ";
if (!m_pElseExpression->ToJavaScript(js, type))
return false;
- js << L"}\n";
}
return !CXFA_IsTooBig(js);
}
diff --git a/xfa/fxfa/fm2js/cxfa_fmexpression.h b/xfa/fxfa/fm2js/cxfa_fmexpression.h
index 88f2d6e4ed..5024432df9 100644
--- a/xfa/fxfa/fm2js/cxfa_fmexpression.h
+++ b/xfa/fxfa/fm2js/cxfa_fmexpression.h
@@ -91,9 +91,11 @@ class CXFA_FMDoExpression : public CXFA_FMExpression {
class CXFA_FMIfExpression : public CXFA_FMExpression {
public:
- CXFA_FMIfExpression(std::unique_ptr<CXFA_FMSimpleExpression> pExpression,
- std::unique_ptr<CXFA_FMExpression> pIfExpression,
- std::unique_ptr<CXFA_FMExpression> pElseExpression);
+ CXFA_FMIfExpression(
+ std::unique_ptr<CXFA_FMSimpleExpression> pExpression,
+ std::unique_ptr<CXFA_FMExpression> pIfExpression,
+ std::vector<std::unique_ptr<CXFA_FMIfExpression>> pElseIfExpressions,
+ std::unique_ptr<CXFA_FMExpression> pElseExpression);
~CXFA_FMIfExpression() override;
bool ToJavaScript(CFX_WideTextBuf& javascript, ReturnType type) override;
@@ -101,6 +103,7 @@ class CXFA_FMIfExpression : public CXFA_FMExpression {
private:
std::unique_ptr<CXFA_FMSimpleExpression> m_pExpression;
std::unique_ptr<CXFA_FMExpression> m_pIfExpression;
+ std::vector<std::unique_ptr<CXFA_FMIfExpression>> m_pElseIfExpressions;
std::unique_ptr<CXFA_FMExpression> m_pElseExpression;
};
diff --git a/xfa/fxfa/fm2js/cxfa_fmparser.cpp b/xfa/fxfa/fm2js/cxfa_fmparser.cpp
index ccd107bb0b..9beda2c564 100644
--- a/xfa/fxfa/fm2js/cxfa_fmparser.cpp
+++ b/xfa/fxfa/fm2js/cxfa_fmparser.cpp
@@ -943,73 +943,46 @@ std::unique_ptr<CXFA_FMExpression> CXFA_FMParser::ParseIfExpression() {
if (HasError() || !IncrementParseDepthAndCheck())
return nullptr;
- // This should be CheckThenNext(TOKif) but we come in here for elseif as well.
- if (!NextToken())
+ if (!CheckThenNext(TOKif))
return nullptr;
- std::unique_ptr<CXFA_FMSimpleExpression> pExpression = ParseParenExpression();
- if (m_token.m_type != TOKthen) {
- m_error = true;
- return nullptr;
- }
- if (!NextToken())
+ std::unique_ptr<CXFA_FMSimpleExpression> pCondition = ParseParenExpression();
+ if (!CheckThenNext(TOKthen))
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));
+ auto pIfExpressions =
+ pdfium::MakeUnique<CXFA_FMBlockExpression>(ParseExpressionList());
- 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;
+ std::vector<std::unique_ptr<CXFA_FMIfExpression>> pElseIfExpressions;
+ while (m_token.m_type == TOKelseif) {
+ if (!NextToken())
+ return nullptr;
- auto else_exprs = ParseExpressionList();
- if (else_exprs.empty() || !CheckThenNext(TOKendif)) {
- m_error = true;
- return nullptr;
- }
+ auto elseIfCondition = ParseParenExpression();
+ if (!CheckThenNext(TOKthen))
+ return nullptr;
- pElseExpression =
- pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(else_exprs));
- break;
- }
- default:
- m_error = true;
+ auto elseIfExprs = ParseExpressionList();
+ pElseIfExpressions.push_back(pdfium::MakeUnique<CXFA_FMIfExpression>(
+ std::move(elseIfCondition),
+ pdfium::MakeUnique<CXFA_FMBlockExpression>(std::move(elseIfExprs)),
+ std::vector<std::unique_ptr<CXFA_FMIfExpression>>(), nullptr));
+ }
+
+ std::unique_ptr<CXFA_FMExpression> pElseExpression;
+ if (m_token.m_type == TOKelse) {
+ if (!NextToken())
return nullptr;
+
+ pElseExpression =
+ pdfium::MakeUnique<CXFA_FMBlockExpression>(ParseExpressionList());
}
- return pdfium::MakeUnique<CXFA_FMIfExpression>(std::move(pExpression),
- std::move(pIfExpression),
- std::move(pElseExpression));
+ if (!CheckThenNext(TOKendif))
+ return nullptr;
+
+ return pdfium::MakeUnique<CXFA_FMIfExpression>(
+ std::move(pCondition), std::move(pIfExpressions),
+ std::move(pElseIfExpressions), std::move(pElseExpression));
}
// While := 'while' '(' SimpleExpression ')' 'do' ExpressionList 'endwhile'
diff --git a/xfa/fxfa/fm2js/cxfa_fmparser_unittest.cpp b/xfa/fxfa/fm2js/cxfa_fmparser_unittest.cpp
index 53ad0ee02b..e939cd954f 100644
--- a/xfa/fxfa/fm2js/cxfa_fmparser_unittest.cpp
+++ b/xfa/fxfa/fm2js/cxfa_fmparser_unittest.cpp
@@ -92,8 +92,7 @@ TEST(CXFA_FMParserTest, Parse) {
L"pfm_rt.dot_acc(border, \"border\", \"fill\", 0, 0), \"\", "
L"\"color\", 0, 0), \"\", \"value\", 0, 0), \"255,64,64\");\n"
L"}\n"
- L"}\nelse\n{\n"
- L"if (pfm_rt.get_val(pfm_rt.neq_op(this, pfm_rt.neg_op(2))))\n"
+ L"}\nelse if (pfm_rt.get_val(pfm_rt.neq_op(this, pfm_rt.neg_op(2))))\n"
L"{\n"
L"if (pfm_rt.is_obj(pfm_rt.dot_acc(pfm_rt.dot_acc(pfm_rt.dot_acc(border, "
L"\"border\", \"fill\", 0, 0), \"\", \"color\", 0, 0), \"\", \"value\", "
@@ -104,7 +103,7 @@ TEST(CXFA_FMParserTest, Parse) {
L"0, 0), \"128,128,128\");\n"
L"}\n"
L"}\n"
- L"else\n{\n{\n"
+ L"else {\n"
L"if (pfm_rt.is_obj(pfm_rt.dot_acc(pfm_rt.dot_acc(pfm_rt.dot_acc("
L"border, \"border\", \"fill\", 0, 0), \"\", \"color\", 0, 0), \"\", "
L"\"value\", 0, 0)))\n{\n"
@@ -113,8 +112,6 @@ TEST(CXFA_FMParserTest, Parse) {
L"\"color\", 0, 0), \"\", \"value\", 0, 0), \"20,170,13\");\n"
L"}\n"
L"}\n"
- L"}\n"
- L"}\n"
L"pfm_ret = this;\n"
L"return pfm_rt.get_val(pfm_ret);\n"
L"}\n).call(this);\n";