views:

8082

answers:

10

I just got the following error in a piece of javascript (in Firefox 3.5, with Firebug running)

cannot access optimized closure

I know, superficially, what caused the error. I had a line

options.length()

instead of

options.length

Fixing this bug, made the message go away. But I'm curious. What does this mean? What is an optimized closure? Is optimizing an enclosure something that the javascript interpretter does automatically? What does it do?

+1  A: 

Seems like a Firefox bug: https://bugzilla.mozilla.org/show_bug.cgi?id=496790

Luca Matteis
I'm getting this message in Firefox, but Chrome halts at the same point in the code.
Killroy
That bug only affected nightlies between Fx 3.0 and 3.5, so it's doubtful that anyone here sees it.
Nickolay
+1  A: 

A closure is a function with context. If you dynamically create a new function, then you create a closure.

function makeAdder(int num) {
    return function(int num2) { return num + num2; }
}

adder = makeAdder(5);
adder(7) // returns (5+7) = 12
adder(2) // returns (5+2) = 7

Here, the closure is the inner function, as returned by makeAdder, along with the '5' that was passed.

The javascript engine might choose to optimize away the function shown above, to make things run faster, never generating or running that code, so it can't be debugged or referenced. Optimizers are supposed to be very careful to ensure there's no impact, so I'd guess this one made a mistake.

davenpcj
You probably meant - `return function(){ ... }`, not `return new function(){ ... }` (as the latter one will actually instantiate a new object using function as constructor). Also, a function does not need to be created "dynamically" to create a closure; any function expression or function declaration closes over free variables in its scope chain (except functions created via `Function`, which are set up to contain only global scope in their scope chain).
kangax
+4  A: 

I had this issue too when Firebug is running.

It seems to happen sometimes, when an exception is raised (for whatever reason) and when there's a recursive function call somewhere in the call stack. The exception gets re-raised as the mysterious "InternalError: cannot access optimized closure"

Changing the way I define the recursive function, seems to make this issue go away. eg changing from

function foo(bar) {... foo(recursively); ...}

to

var foo = function(bar) {... foo(recursively); ...}

Hope that helps.

Matthew
I had this problem with a recursive function, and this fixed it for me! Thanks!
Skilldrick
Cheers. As it happens it turned out that whether the function is called recursively or not doesn't make a difference, it was just declaring it in this way nested within another function which caused the problem.
Matthew
This fixed it for me as well. It wasn't a recursive function either.
Mike Nelson
A: 

I encountered the same error today. In my case this occurred because I was referencing an object's attribute or function that did not exist or was not available. I'm guessing that since the object was available via a closure that was optimized, firebug could not access metadata on that object and thus the cryptic error message.

Bryan Matthews
+3  A: 

It is a bug in Firefox happening with Firebug open:

https://bugzilla.mozilla.org/show_bug.cgi?id=505001

[An earlier answer mentioned this was due to this other bug, which I think is incorrect as that other problem was not related to Firebug.]

Alessandro Vernet
Comments on that bug seem to indicate that this is fixed in Firefox 3.6. Yay! If anyone sees this on 3.6, please bring this up in a firebug newsgroup.
Nickolay
A: 

This also happened to me today. Firebug error'd at line 2 of this function:

function IsValidDate(objName) {
  re = new RegExp('^( +|today|pdate|- *\\d+ *(day(s|)|week(s|))+ *$', 'i');
  if (re.test(objName.value)) return 2;
  return (chkdate(objName));
}

When I added "var " before the declaration of "re" in line 1, the error went away.

spthorn
A: 

i had the same problem, but it was my fault

var arr = [];

to this

var arr = new Array(3);
sacabuche
A: 

There is an exception being raised somewhere else in your code within the function that has this error. It could be as simple trying to access a variable that doesn't exist.

I think we need to get a Firebug dev in here to answer why it doesn't give a more specific error as to where in the closure that raised the exception to prompt the error.

You pasted options.length(), but it is not what prompted the error. What caused the error is the fact that your bug was inside a closure.

function(){
    array.length()
}

that gives the error

resopollution
A: 

This can also be caused by a simple race condition. I was just refactoring a 'startup' object that does a few things before the document is ready. As soon as I tried to access a second object defined immediately below the startup object I received this error.

I was under the impression that script execution waited until all of the code was compiled. Clearly that's not the case. Waiting for document ready to call methods on the second object fixed the problem. Also, using this nice 'dump()' function confirms that the second object is only partially defined when the error occurs: http://www.openjs.com/scripts/others/dump_function_php_print_r.php

c.cobb