[HtmlUnit] [htmlunit:bugs] #1980 [corejs] Quirky handling of named function expression
RBRi via HtmlUnit-develop <[email protected]> Fri, 10 Aug 2018 06:11:21 -0000
| Newsgroups | gmane.comp.java.htmlunit.devel |
|---|---|
| Message-ID | </p/htmlunit/bugs/1980/c4e940bd32b2e93647a71af5a330a012c7e0dcff.bugs@htmlunit.p.sourceforge.net> |
BTW: will inform on twitter if a new SNASPHOT build is available
---
** [bugs:#1980] [corejs] Quirky handling of named function expression**
**Status:** closed
**Group:** Latest SVN
**Created:** Sun Aug 05, 2018 12:28 PM UTC by Atsushi Nakagawa
**Last Updated:** Fri Aug 10, 2018 06:10 AM UTC
**Owner:** RBRi
**Attachments:**
- [test1.html](https://sourceforge.net/p/htmlunit/bugs/1980/attachment/test1.html) (194 Bytes; text/html)
- [test2.html](https://sourceforge.net/p/htmlunit/bugs/1980/attachment/test2.html) (275 Bytes; text/html)
- [test3.html](https://sourceforge.net/p/htmlunit/bugs/1980/attachment/test3.html) (227 Bytes; text/html)
- [test4.html](https://sourceforge.net/p/htmlunit/bugs/1980/attachment/test4.html) (182 Bytes; text/html)
- [test5.html](https://sourceforge.net/p/htmlunit/bugs/1980/attachment/test5.html) (1.2 kB; text/html)
Attached are five tests for testing various aspects of **[named function expressions](https://stackoverflow.com/questions/15336347)** in htmlunit.
As at 2.32, support for them are *quirky*, leading to subtly misinterpreted JS that are hard to debug.
For example, the following code from `test1.html` incorrectly throws a `ScriptException: ReferenceError: Assignment to undefined "abc" in strict mode` on the second line.
```javascript
'use strict';
var abc = 1;
var foo = function abc() {}
```
This code from `test2.html` should print `a` followed by `b`. Instead `b` is printed twice. (Unfortunatley, code like this is all too common for minimized scripts.)
```javascript
var a = function () {
var x = (function x () { console.log("a") })
return function () { x() }
}()
var b = function () {
var x = (function x () { console.log("b") })
return function () { x() }
}()
a()
b()
```
### Test cases
Five tests `test1.html` to `test5.html` are attached. Expectations are as follows:
`test1.html`:
```java
final String[] expected = {
"INFO: outer abc = 1.0",
"INFO: inner abc = (function abc() { console.log(\"inner abc = \", abc); })",
};
```
`test2.html`:
```java
final String[] expected = {
"INFO: a",
"INFO: b",
};
```
`test3.html`:
```java
final String[] expected = {
"INFO: a",
};
```
`test4.html`:
```java
final String[] expected = {
"INFO: (function func() { console.log(func); })",
"INFO: outer",
};
```
`test5.html`:
```java
final String[] expected = {
"INFO: f1",
"INFO: f2",
"INFO: f3",
"INFO: !f4",
"INFO: f5",
"INFO: !f6",
"INFO: !f7",
"INFO: !f8",
"INFO: f10",
"INFO: f11",
"INFO: f12",
"INFO: f10", // Chrome/FF: !f10
"INFO: f11",
"INFO: f12",
"INFO: f13",
};
```
### Possible fix
While rhino far surpasses my coding ability, asashour [seems to have](https://github.com/HtmlUnit/htmlunit-rhino-fork/commit/afadfd48770eace84c70f503efef66c5767c9a3b) already added the [necessary building block](https://github.com/HtmlUnit/htmlunit-rhino-fork/blob/e7ce0f761305d876f99a323a27214f064c5fb4f3/src/org/mozilla/javascript/InterpreterData.java#L98) for this.
The following is the code I'm using to further this for a fix:
```diff
--- a/src/main/java/net/sourceforge/htmlunit/corejs/javascript/CodeGenerator.java
+++ b/src/main/java/net/sourceforge/htmlunit/corejs/javascript/CodeGenerator.java
@@ -6,12 +6,12 @@
package net.sourceforge.htmlunit.corejs.javascript;
-import net.sourceforge.htmlunit.corejs.javascript.ast.AstNode;
-import net.sourceforge.htmlunit.corejs.javascript.ast.FunctionCall;
+import net.sourceforge.htmlunit.corejs.javascript.ast.AstRoot;
+import net.sourceforge.htmlunit.corejs.javascript.ast.Block;
import net.sourceforge.htmlunit.corejs.javascript.ast.FunctionNode;
import net.sourceforge.htmlunit.corejs.javascript.ast.Jump;
+import net.sourceforge.htmlunit.corejs.javascript.ast.Scope;
import net.sourceforge.htmlunit.corejs.javascript.ast.ScriptNode;
-import net.sourceforge.htmlunit.corejs.javascript.ast.UnaryExpression;
import net.sourceforge.htmlunit.corejs.javascript.ast.VariableInitializer;
/**
@@ -197,11 +197,10 @@ private void generateNestedFunctions()
gen.itsData = new InterpreterData(itsData);
gen.generateFunctionICode();
array[i] = gen.itsData;
- if (fn.getParent() instanceof FunctionCall) {
- AstNode grandParent = fn.getParent().getParent();
- if (grandParent instanceof UnaryExpression && grandParent.getType() == Token.NOT) {
- gen.itsData.declaredAsFunctionExpression = true;
- }
+ if (!(fn.getParent() instanceof AstRoot ||
+ fn.getParent() instanceof Scope ||
+ fn.getParent() instanceof Block)) {
+ gen.itsData.declaredAsFunctionExpression = true;
}
}
itsData.itsNestedFunctions = array;
```
---
Sent from sourceforge.net because [email protected] is subscribed to https://sourceforge.net/p/htmlunit/bugs/
To unsubscribe from further messages, a project admin can change settings at https://sourceforge.net/p/htmlunit/admin/bugs/options. Or, if this is a mailing list, you can unsubscribe from the mailing list.
------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
_______________________________________________
HtmlUnit-develop mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/htmlunit-develop