开发者

Eval bug in Rhino inside a try/catch

开发者 https://www.devze.com 2023-03-11 10:59 出处:网络
Ok, I think I found a bug in Rhino.I am trying to dynamically eval code in the global scope, and it works fine if I just do eval.call(null, \"code to eval\");All was well until I tried to capture exce

Ok, I think I found a bug in Rhino. I am trying to dynamically eval code in the global scope, and it works fine if I just do eval.call(null, "code to eval"); All was well until I tried to capture exceptions. When I surround that code with try/catch, the code is not actually eval'ed in the global context.

To illustrate the bug:

function works(str) {
  eval.call(null, str);
}

function doesntWork(str, count) {
  try {
    eval.call(null, str);
  } catch (e) {
    println('Error in ' + count + ' call: ' + e);
  }
}

works('var abc = 123;');
works('println("The value: " + abc);');
doesntWork('var xyz = 123;', 'first');
doesntWork('println("The value: " + xyz);', 'second');

When I run this in the Rhino built into OpenJDK 6, I get:

The value: 123
Error in second call: ReferenceError: "xyz" is not defined.

I was more convinced of this being a bug when I changed the println's to console.log and ran it in Chrome, at which point I got 2 "The value: 123" logs, which is as I expect.

Furthermore, I looked up the ECMAScript standard and got this:

10.4.2 Entering Eval Code

The following steps are performed when control enters the execution context for eval code:

  1. If there is no calling context or if the eval code is not being evaluated by a direct call (15.1.2.1.1) to the eval function then,
    1. Initialize the execution context as if it was a global execution context using the eval code as C as described in 10.4.1.1.
  2. Else,
    1. Set the ThisBinding to the same value as the ThisBinding of the calling execution context.
    2. Set the LexicalEnvironment to the same value as the LexicalEnvironment of the calling execution context.
    3. Set the VariableEnvironment to the same value as the VariableEnvironment of the calling execution context.
  3. If the eval code is strict code, then
    1. Let strictVarEnv be the result of calling NewDeclarativeEnvironment passing the LexicalEnvironment as the argument.
    2. Set the LexicalEnvironment to strictVarEnv.
    3. Set the VariableEnvironment to strictVarEnv.
  4. Perform Declaration Binding Instantiation as des开发者_运维问答cribed in 10.5 using the eval code.

The first point is my case, or "there is no calling context," so this should be eval'ed in the global context, and my xyz variable should work fine.

Have I truly hit a Rhino bug, or am I missing something?


The Rhino code built into the JDK is really, really old, and it has lots of bugs that have been fixed (for a long time) in the current release of the software from Mozilla.

If you're starting a new project, I would strongly recommend that you look into what it's like to integrate Rhino using only the from-Mozilla code, and just make believe that all the "ScriptEngine" stuff in 1.6 isn't there (or, possibly, implement your own ScriptEngine code around the Mozilla stuff). Don't make the same mistake I made. Twice. :-(

0

精彩评论

暂无评论...
验证码 换一张
取 消