summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorShashwat Dixit <shashwatdixit124@gmail.com>2017-02-02 11:21:10 (GMT)
committerMilian Wolff <mail@milianw.de>2017-02-02 11:22:18 (GMT)
commit2bcdaa11f4d37b14cc0e016df9017224ca03f8d4 (patch)
tree04f098c31b90b7e6017cc460871905a0fbe86603
parent5fa82a61f7cfd230b8ed7cce1a937eed6a2f4eac (diff)
Php7 IIFE syntax parsing
Added parsing support for php7 iife syntax. Reviewers: kfunk, #kdevelop, mwolff Reviewed By: #kdevelop, mwolff Subscribers: kdevelop-devel Tags: #kdevelop BUG: 370515 Differential Revision: https://phabricator.kde.org/D4391
-rw-r--r--duchain/tests/duchain.cpp31
-rw-r--r--duchain/tests/duchain.h2
-rw-r--r--parser/php.g8
3 files changed, 39 insertions, 2 deletions
diff --git a/duchain/tests/duchain.cpp b/duchain/tests/duchain.cpp
index 8144487..bc9684f 100644
--- a/duchain/tests/duchain.cpp
+++ b/duchain/tests/duchain.cpp
@@ -2834,6 +2834,37 @@ void TestDUChain::closureEmptyUse()
QCOMPARE(top->problems().size(), 1);
}
+void TestDUChain::iifeParser()
+{
+ // testcase for bug https://bugs.kde.org/show_bug.cgi?id=370515
+ TopDUContext* top = parse("<?php\n"
+ "$lambda1 = (function() {return 5;})();\n"
+ "$lambda2 = (function($a) {return $a;})(50);\n"
+ "$lambda3 = (function($a){ return function($b) use ($a){echo $a + $b;};})(50); \n"
+ "$lambda4 = (function ($a){echo $a;})(10) + (function ($a){echo $a ;})(20);"
+ , DumpNone);
+
+ QVERIFY(top);
+
+ DUChainReleaser releaseTop(top);
+ DUChainWriteLocker lock;
+ QVERIFY(top->problems().empty());
+}
+
+void TestDUChain::iife()
+{
+ TopDUContext* top = parse("<?php $l = (function($a){ return function($b) use ($a){echo $a + $b;};})(50); \n", DumpNone);
+ QVERIFY(top);
+ DUChainReleaser releaseTop(top);
+ DUChainWriteLocker lock;
+ QVERIFY(top->problems().isEmpty());
+ QCOMPARE(top->localDeclarations().count(), 2);
+ Declaration* l = top->localDeclarations().first();
+ QCOMPARE(l->identifier().toString(), QString("l"));
+ Declaration* iife = top->localDeclarations().last();
+ QVERIFY(iife->identifier().isEmpty());
+}
+
void TestDUChain::gotoTest()
{
TopDUContext* top = parse("<?php goto dest; dest: \n", DumpNone);
diff --git a/duchain/tests/duchain.h b/duchain/tests/duchain.h
index 31db9d0..c9fe0a5 100644
--- a/duchain/tests/duchain.h
+++ b/duchain/tests/duchain.h
@@ -142,6 +142,8 @@ private slots:
void closureParser();
void closures();
void closureEmptyUse();
+ void iifeParser();
+ void iife();
void gotoTest();
void ternary();
void bug296709();
diff --git a/parser/php.g b/parser/php.g
index abe57a9..4975d14 100644
--- a/parser/php.g
+++ b/parser/php.g
@@ -546,8 +546,8 @@ expression=booleanOrExpression
| varExpressionArray=varExpressionArray arrayIndex=arrayIndexSpecifier*
-> varExpression ;;
-
- LPAREN try/rollback (newObject=varExpressionNewObject RPAREN (#variableProperties=instantiationAccess*))
+ (?[: LA(1).kind == Token_LPAREN && LA(2).kind == Token_FUNCTION && LA(3).kind == Token_LPAREN :] iife=iifeSyntax )
+ | LPAREN try/rollback (newObject=varExpressionNewObject RPAREN (#variableProperties=instantiationAccess*))
catch (expression=expr RPAREN)
| BACKTICK encapsList=encapsList BACKTICK
--try/rollback resolves conflict scalar vs. staticMember (foo::bar vs. foo::$bar)
@@ -579,6 +579,10 @@ expression=booleanOrExpression
LBRACE try/recover(functionBody=innerStatementList) RBRACE
-> closure ;;
+ LPAREN try/rollback (closure=closure RPAREN LPAREN parameterList=functionCallParameterList RPAREN)
+ catch (expression=expr RPAREN)
+-> iifeSyntax ;;
+
(#lexicalVars=lexicalVar @ COMMA) | 0 [: reportProblem(Error, QStringLiteral("Use list of closure must not be empty.")); :]
-> lexicalVarList ;;