47
47
import java .util .Set ;
48
48
49
49
import com .oracle .graal .python .PythonLanguage ;
50
+ import com .oracle .graal .python .builtins .PythonBuiltinClassType ;
50
51
import com .oracle .graal .python .builtins .objects .cell .PCell ;
52
+ import com .oracle .graal .python .builtins .objects .common .HashingStorage ;
53
+ import com .oracle .graal .python .builtins .objects .dict .PDict ;
51
54
import com .oracle .graal .python .builtins .objects .function .Arity ;
55
+ import com .oracle .graal .python .builtins .objects .function .PArguments ;
56
+ import com .oracle .graal .python .builtins .objects .function .PFunction ;
52
57
import com .oracle .graal .python .builtins .objects .object .PythonBuiltinObject ;
58
+ import com .oracle .graal .python .builtins .objects .str .PString ;
53
59
import com .oracle .graal .python .builtins .objects .type .LazyPythonClass ;
54
60
import com .oracle .graal .python .nodes .ModuleRootNode ;
55
61
import com .oracle .graal .python .nodes .PRootNode ;
@@ -127,6 +133,7 @@ public PCode(LazyPythonClass cls, RootCallTarget callTarget) {
127
133
}
128
134
}
129
135
136
+ @ TruffleBoundary
130
137
public PCode (LazyPythonClass cls , int argcount , int kwonlyargcount ,
131
138
int nlocals , int stacksize , int flags ,
132
139
byte [] codestring , Object [] constants , Object [] names ,
@@ -150,15 +157,60 @@ public PCode(LazyPythonClass cls, int argcount, int kwonlyargcount,
150
157
this .cellvars = cellvars ;
151
158
152
159
// Derive a new call target from the code string, if we can
153
- FrameDescriptor frameDescriptor = new FrameDescriptor ();
154
- MaterializedFrame frame = Truffle .getRuntime ().createMaterializedFrame (new Object [0 ], frameDescriptor );
155
- for (int i = 0 ; i < freevars .length ; i ++) {
156
- Object ident = freevars [i ];
157
- FrameSlot slot = frameDescriptor .addFrameSlot (ident );
158
- frameDescriptor .setFrameSlotKind (slot , FrameSlotKind .Object );
159
- frame .setObject (slot , new PCell ());
160
+ RootNode rootNode = null ;
161
+ if ((flags & FLAG_MODULE ) == 0 ) {
162
+ // we're looking for the function, not the module
163
+ String funcdef ;
164
+ if (freevars .length > 0 ) {
165
+ // we build an outer function to provide the initial scoping
166
+ String outernme = "_____" + System .nanoTime ();
167
+ StringBuilder sb = new StringBuilder ();
168
+ sb .append ("def " ).append (outernme ).append ("():\n " );
169
+ for (Object freevar : freevars ) {
170
+ String v ;
171
+ if (freevar instanceof PString ) {
172
+ v = ((PString ) freevar ).getValue ();
173
+ } else if (freevar instanceof String ) {
174
+ v = (String ) freevar ;
175
+ } else {
176
+ continue ;
177
+ }
178
+ sb .append (" " ).append (v ).append (" = None\n " );
179
+ }
180
+ sb .append (" global " ).append (name ).append ("\n " );
181
+ sb .append (" " ).append (new String (codestring ));
182
+ sb .append ("\n \n " ).append (outernme ).append ("()" );
183
+ funcdef = sb .toString ();
184
+ } else {
185
+ funcdef = new String (codestring );
186
+ }
187
+
188
+ rootNode = (RootNode ) PythonLanguage .getCore ().getParser ().parse (ParserMode .File , PythonLanguage .getCore (), Source .newBuilder ("python" , funcdef , name ).build (), null );
189
+ Object [] args = PArguments .create ();
190
+ PDict globals = PythonLanguage .getCore ().factory ().createDict ();
191
+ PArguments .setGlobals (args , globals );
192
+ Truffle .getRuntime ().createCallTarget (rootNode ).call (args );
193
+ Object function = globals .getDictStorage ().getItem (name , HashingStorage .getSlowPathEquivalence (name ));
194
+ if (function instanceof PFunction ) {
195
+ rootNode = ((PFunction ) function ).getFunctionRootNode ();
196
+ } else {
197
+ throw PythonLanguage .getCore ().raise (PythonBuiltinClassType .ValueError , "got an invalid codestring trying to create a function code object" );
198
+ }
199
+ } else {
200
+ MaterializedFrame frame = null ;
201
+ if (freevars .length > 0 ) {
202
+ FrameDescriptor frameDescriptor = new FrameDescriptor ();
203
+ frame = Truffle .getRuntime ().createMaterializedFrame (new Object [0 ], frameDescriptor );
204
+ for (int i = 0 ; i < freevars .length ; i ++) {
205
+ Object ident = freevars [i ];
206
+ FrameSlot slot = frameDescriptor .addFrameSlot (ident );
207
+ frameDescriptor .setFrameSlotKind (slot , FrameSlotKind .Object );
208
+ frame .setObject (slot , new PCell ());
209
+ }
210
+ }
211
+ rootNode = (RootNode ) PythonLanguage .getCore ().getParser ().parse (ParserMode .File , PythonLanguage .getCore (), Source .newBuilder ("python" , new String (codestring ), name ).build (), frame );
212
+ assert rootNode instanceof ModuleRootNode ;
160
213
}
161
- RootNode rootNode = (RootNode ) PythonLanguage .getCore ().getParser ().parse (ParserMode .File , PythonLanguage .getCore (), Source .newBuilder ("python" , new String (codestring ), name ).build (), frame );
162
214
this .callTarget = Truffle .getRuntime ().createCallTarget (rootNode );
163
215
164
216
char paramNom = 'A' ;
0 commit comments