7979d7818ba856ca5f3d0fa55bea5120eba55d47
[org.ibex.core.git] / src / org / mozilla / javascript / InterpretedFunction.java
1 /* -*- Mode: java; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-\r
2  *\r
3  * The contents of this file are subject to the Netscape Public\r
4  * License Version 1.1 (the "License"); you may not use this file\r
5  * except in compliance with the License. You may obtain a copy of\r
6  * the License at http://www.mozilla.org/NPL/\r
7  *\r
8  * Software distributed under the License is distributed on an "AS\r
9  * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express oqr\r
10  * implied. See the License for the specific language governing\r
11  * rights and limitations under the License.\r
12  *\r
13  * The Original Code is Rhino code, released\r
14  * May 6, 1999.\r
15  *\r
16  * The Initial Developer of the Original Code is Netscape\r
17  * Communications Corporation.  Portions created by Netscape are\r
18  * Copyright (C) 1997-2000 Netscape Communications Corporation. All\r
19  * Rights Reserved.\r
20  *\r
21  * Contributor(s): \r
22  * Roger Lawrence\r
23  *\r
24  * Alternatively, the contents of this file may be used under the\r
25  * terms of the GNU Public License (the "GPL"), in which case the\r
26  * provisions of the GPL are applicable instead of those above.\r
27  * If you wish to allow use of your version of this file only\r
28  * under the terms of the GPL and not to allow others to use your\r
29  * version of this file under the NPL, indicate your decision by\r
30  * deleting the provisions above and replace them with the notice\r
31  * and other provisions required by the GPL.  If you do not delete\r
32  * the provisions above, a recipient may use your version of this\r
33  * file under either the NPL or the GPL.\r
34  */\r
35 \r
36 package org.mozilla.javascript;\r
37 \r
38 import java.util.*;\r
39 import org.mozilla.javascript.debug.DebuggableScript;\r
40 \r
41 public class InterpretedFunction extends NativeFunction implements DebuggableScript {\r
42     \r
43     InterpretedFunction(Context cx,\r
44                         InterpreterData theData, \r
45                         String[] argNames, short argCount)\r
46     {\r
47         itsData = theData;\r
48         this.argNames = argNames;\r
49         this.argCount = argCount;\r
50         init(cx);\r
51     }\r
52     \r
53     void init(Context cx)\r
54     {\r
55         functionName = itsData.itsName;\r
56         source = itsData.itsSource;\r
57         nestedFunctions = itsData.itsNestedFunctions;\r
58         if (cx != null)\r
59             version = (short)cx.getLanguageVersion();\r
60     }\r
61     \r
62     InterpretedFunction(InterpretedFunction theOther,\r
63                         Scriptable theScope, Context cx)\r
64     {\r
65         itsData = theOther.itsData;\r
66         this.argNames = theOther.argNames;\r
67         this.argCount = theOther.argCount;\r
68         itsClosure = theScope;\r
69         init(cx);\r
70     }\r
71     \r
72     public Object call(Context cx, Scriptable scope, Scriptable thisObj,\r
73                        Object[] args)\r
74         throws JavaScriptException\r
75     {            \r
76         Function temp = cx.currentFunction;\r
77         if (cx.stackDepth++ > 200) {\r
78             NativeError ne = new NativeError();\r
79             ne.put("message", ne, "maximum interpreter stack depth limit exceeded");\r
80             cx.stackDepth--;\r
81             throw new EcmaError(ne, cx.interpreterSourceFile, cx.interpreterLine, 0, "");\r
82         }\r
83         cx.currentFunction = this;\r
84         cx.interpreterSourceFile = itsData.itsSourceFile;\r
85         if (itsClosure != null)\r
86             scope = itsClosure;\r
87         else if (!itsData.itsUseDynamicScope)\r
88             scope = getParentScope();\r
89 \r
90         if (itsData.itsCheckThis) \r
91             thisObj = ScriptRuntime.getThis(thisObj);\r
92         \r
93         if (itsData.itsNeedsActivation) {\r
94             scope = ScriptRuntime.initVarObj(cx, scope, this, thisObj, args);\r
95         }\r
96         try {\r
97             return Interpreter.interpret(cx, scope, thisObj, args, this,\r
98                                          itsData);\r
99         } finally {\r
100             if (itsData.itsNeedsActivation) {\r
101                 ScriptRuntime.popActivation(cx);\r
102             }\r
103             cx.currentFunction = temp;\r
104             cx.stackDepth--;\r
105         }\r
106     }\r
107     \r
108     public boolean isFunction() {\r
109         return true;\r
110     }\r
111     \r
112     public Scriptable getScriptable() {\r
113         return this;\r
114     }\r
115     \r
116     public String getSourceName() {\r
117         return itsData.itsSourceFile;\r
118     }\r
119     \r
120     public int[] getLineNumbers() { \r
121         return itsData.itsLineNumberTable.getKeys();\r
122     }\r
123     \r
124     public boolean placeBreakpoint(int line) { // XXX throw exn?\r
125         return itsData.placeBreakpoint(line);\r
126     }\r
127     \r
128     public boolean removeBreakpoint(int line) {\r
129         return itsData.removeBreakpoint(line);\r
130     }\r
131     \r
132     InterpreterData itsData;\r
133     Scriptable itsClosure;\r
134 }\r
135     \r