PageRenderTime 67ms CodeModel.GetById 22ms RepoModel.GetById 0ms app.codeStats 1ms

/src/org/python/compiler/CodeCompiler.java

http://github.com/nriley/jython
Java | 2443 lines | 1949 code | 366 blank | 128 comment | 370 complexity | 1397420fd7ba05d3a2c32bdaecccbfe2 MD5 | raw file

Large files files are truncated, but you can click here to view the full file

  1. // Copyright (c) Corporation for National Research Initiatives
  2. package org.python.compiler;
  3. import java.io.IOException;
  4. import java.util.ArrayList;
  5. import java.util.Collection;
  6. import java.util.Map;
  7. import java.util.Stack;
  8. import java.util.Vector;
  9. import org.python.antlr.ParseException;
  10. import org.python.antlr.PythonTree;
  11. import org.python.antlr.Visitor;
  12. import org.python.antlr.ast.Assert;
  13. import org.python.antlr.ast.Assign;
  14. import org.python.antlr.ast.Attribute;
  15. import org.python.antlr.ast.AugAssign;
  16. import org.python.antlr.ast.BinOp;
  17. import org.python.antlr.ast.BoolOp;
  18. import org.python.antlr.ast.Break;
  19. import org.python.antlr.ast.Call;
  20. import org.python.antlr.ast.ClassDef;
  21. import org.python.antlr.ast.Compare;
  22. import org.python.antlr.ast.Continue;
  23. import org.python.antlr.ast.Delete;
  24. import org.python.antlr.ast.Dict;
  25. import org.python.antlr.ast.Ellipsis;
  26. import org.python.antlr.ast.ExceptHandler;
  27. import org.python.antlr.ast.Exec;
  28. import org.python.antlr.ast.Expr;
  29. import org.python.antlr.ast.Expression;
  30. import org.python.antlr.ast.ExtSlice;
  31. import org.python.antlr.ast.For;
  32. import org.python.antlr.ast.FunctionDef;
  33. import org.python.antlr.ast.GeneratorExp;
  34. import org.python.antlr.ast.Global;
  35. import org.python.antlr.ast.If;
  36. import org.python.antlr.ast.IfExp;
  37. import org.python.antlr.ast.Import;
  38. import org.python.antlr.ast.ImportFrom;
  39. import org.python.antlr.ast.Index;
  40. import org.python.antlr.ast.Interactive;
  41. import org.python.antlr.ast.Lambda;
  42. import org.python.antlr.ast.List;
  43. import org.python.antlr.ast.ListComp;
  44. import org.python.antlr.ast.Name;
  45. import org.python.antlr.ast.Num;
  46. import org.python.antlr.ast.Pass;
  47. import org.python.antlr.ast.Print;
  48. import org.python.antlr.ast.Raise;
  49. import org.python.antlr.ast.Repr;
  50. import org.python.antlr.ast.Return;
  51. import org.python.antlr.ast.Slice;
  52. import org.python.antlr.ast.Str;
  53. import org.python.antlr.ast.Subscript;
  54. import org.python.antlr.ast.Suite;
  55. import org.python.antlr.ast.TryExcept;
  56. import org.python.antlr.ast.TryFinally;
  57. import org.python.antlr.ast.Tuple;
  58. import org.python.antlr.ast.UnaryOp;
  59. import org.python.antlr.ast.While;
  60. import org.python.antlr.ast.With;
  61. import org.python.antlr.ast.Yield;
  62. import org.python.antlr.ast.alias;
  63. import org.python.antlr.ast.cmpopType;
  64. import org.python.antlr.ast.comprehension;
  65. import org.python.antlr.ast.expr_contextType;
  66. import org.python.antlr.ast.keyword;
  67. import org.python.antlr.ast.operatorType;
  68. import org.python.antlr.base.expr;
  69. import org.python.antlr.base.mod;
  70. import org.python.antlr.base.stmt;
  71. import org.python.core.CompilerFlags;
  72. import org.python.core.ContextGuard;
  73. import org.python.core.ContextManager;
  74. import org.python.core.PyComplex;
  75. import org.python.core.PyFloat;
  76. import org.python.core.PyInteger;
  77. import org.python.core.PyLong;
  78. import org.python.core.PyObject;
  79. import org.python.core.PyString;
  80. import org.python.core.PyUnicode;
  81. import org.objectweb.asm.ClassWriter;
  82. import org.objectweb.asm.Label;
  83. import org.objectweb.asm.Opcodes;
  84. import org.objectweb.asm.Type;
  85. import org.objectweb.asm.commons.Method;
  86. public class CodeCompiler extends Visitor implements Opcodes, ClassConstants //, PythonGrammarTreeConstants
  87. {
  88. public static final Object Exit=new Integer(1);
  89. public static final Object NoExit=null;
  90. public static final int GET=0;
  91. public static final int SET=1;
  92. public static final int DEL=2;
  93. public static final int AUGGET=3;
  94. public static final int AUGSET=4;
  95. public Module module;
  96. public ClassWriter cw;
  97. public Code code;
  98. public CodeCompiler mrefs;
  99. public CompilerFlags cflags;
  100. int temporary;
  101. expr_contextType augmode;
  102. int augtmp1;
  103. int augtmp2;
  104. int augtmp3;
  105. int augtmp4;
  106. public boolean fast_locals, print_results;
  107. public Map<String, SymInfo> tbl;
  108. public ScopeInfo my_scope;
  109. boolean optimizeGlobals = true;
  110. public Vector names;
  111. public String className;
  112. public Stack continueLabels, breakLabels;
  113. public Stack exceptionHandlers;
  114. public Vector yields = new Vector();
  115. /* break/continue finally's level.
  116. * This is the lowest level in the exceptionHandlers which should
  117. * be executed at break or continue.
  118. * It is saved/updated/restored when compiling loops.
  119. * A similar level for returns is not needed because a new CodeCompiler
  120. * is used for each PyCode, ie. each 'function'.
  121. * When returning through finally's all the exceptionHandlers are executed.
  122. */
  123. public int bcfLevel = 0;
  124. int yield_count = 0;
  125. private Stack<String> stack = new Stack<String>();
  126. public CodeCompiler(Module module, boolean print_results) {
  127. this.module = module;
  128. this.print_results = print_results;
  129. mrefs = this;
  130. cw = module.classfile.cw;
  131. continueLabels = new Stack();
  132. breakLabels = new Stack();
  133. exceptionHandlers = new Stack();
  134. }
  135. public void getNone() throws IOException {
  136. code.getstatic("org/python/core/Py", "None", $pyObj);
  137. }
  138. public void loadFrame() throws Exception {
  139. code.aload(1);
  140. }
  141. public void loadThreadState() throws Exception {
  142. code.aload(2);
  143. }
  144. public void setLastI(int idx) throws Exception {
  145. loadFrame();
  146. code.iconst(idx);
  147. code.putfield("org/python/core/PyFrame", "f_lasti", "I");
  148. }
  149. private void loadf_back() throws Exception {
  150. code.getfield("org/python/core/PyFrame", "f_back", $pyFrame);
  151. }
  152. public int storeTop() throws Exception {
  153. int tmp = code.getLocal("org/python/core/PyObject");
  154. code.astore(tmp);
  155. return tmp;
  156. }
  157. public void setline(int line) throws Exception {
  158. if (module.linenumbers) {
  159. code.setline(line);
  160. loadFrame();
  161. code.iconst(line);
  162. code.invokevirtual("org/python/core/PyFrame", "setline", "(I)V");
  163. }
  164. }
  165. public void setline(PythonTree node) throws Exception {
  166. setline(node.getLine());
  167. }
  168. public void set(PythonTree node) throws Exception {
  169. int tmp = storeTop();
  170. set(node, tmp);
  171. code.aconst_null();
  172. code.astore(tmp);
  173. code.freeLocal(tmp);
  174. }
  175. public void set(PythonTree node, int tmp) throws Exception {
  176. temporary = tmp;
  177. visit(node);
  178. }
  179. private void saveAugTmps(PythonTree node, int count) throws Exception {
  180. if (count >= 4) {
  181. augtmp4 = code.getLocal("Lorg/python/core/PyObject;");
  182. code.astore(augtmp4);
  183. }
  184. if (count >= 3) {
  185. augtmp3 = code.getLocal("Lorg/python/core/PyObject;");
  186. code.astore(augtmp3);
  187. }
  188. if (count >= 2) {
  189. augtmp2 = code.getLocal("Lorg/python/core/PyObject;");
  190. code.astore(augtmp2);
  191. }
  192. augtmp1 = code.getLocal("Lorg/python/core/PyObject;");
  193. code.astore(augtmp1);
  194. code.aload(augtmp1);
  195. if (count >= 2)
  196. code.aload(augtmp2);
  197. if (count >= 3)
  198. code.aload(augtmp3);
  199. if (count >= 4)
  200. code.aload(augtmp4);
  201. }
  202. private void restoreAugTmps(PythonTree node, int count) throws Exception {
  203. code.aload(augtmp1);
  204. code.freeLocal(augtmp1);
  205. if (count == 1)
  206. return;
  207. code.aload(augtmp2);
  208. code.freeLocal(augtmp2);
  209. if (count == 2)
  210. return;
  211. code.aload(augtmp3);
  212. code.freeLocal(augtmp3);
  213. if (count == 3)
  214. return;
  215. code.aload(augtmp4);
  216. code.freeLocal(augtmp4);
  217. }
  218. public void parse(mod node, Code code,
  219. boolean fast_locals, String className,
  220. boolean classBody, ScopeInfo scope, CompilerFlags cflags)
  221. throws Exception
  222. {
  223. this.fast_locals = fast_locals;
  224. this.className = className;
  225. this.code = code;
  226. this.cflags = cflags;
  227. my_scope = scope;
  228. names = scope.names;
  229. tbl = scope.tbl;
  230. optimizeGlobals = fast_locals&&!scope.exec&&!scope.from_import_star;
  231. if (scope.max_with_count > 0) {
  232. // allocate for all the with-exits we will have in the frame;
  233. // this allows yield and with to happily co-exist
  234. loadFrame();
  235. code.iconst(scope.max_with_count);
  236. code.anewarray("org/python/core/PyObject");
  237. code.putfield("org/python/core/PyFrame", "f_exits", $pyObjArr);
  238. }
  239. Object exit = visit(node);
  240. if (classBody) {
  241. loadFrame();
  242. code.invokevirtual("org/python/core/PyFrame", "getf_locals", "()" + $pyObj);
  243. code.areturn();
  244. } else {
  245. if (exit == null) {
  246. setLastI(-1);
  247. getNone();
  248. code.areturn();
  249. }
  250. }
  251. }
  252. @Override
  253. public Object visitInteractive(Interactive node) throws Exception {
  254. traverse(node);
  255. return null;
  256. }
  257. @Override
  258. public Object visitModule(org.python.antlr.ast.Module suite)
  259. throws Exception
  260. {
  261. if (suite.getInternalBody().size() > 0 &&
  262. suite.getInternalBody().get(0) instanceof Expr &&
  263. ((Expr) suite.getInternalBody().get(0)).getInternalValue() instanceof Str)
  264. {
  265. loadFrame();
  266. code.ldc("__doc__");
  267. visit(((Expr) suite.getInternalBody().get(0)).getInternalValue());
  268. code.invokevirtual("org/python/core/PyFrame", "setglobal", "(" +$str + $pyObj + ")V");
  269. }
  270. traverse(suite);
  271. return null;
  272. }
  273. @Override
  274. public Object visitExpression(Expression node) throws Exception {
  275. if (my_scope.generator && node.getInternalBody() != null) {
  276. module.error("'return' with argument inside generator",
  277. true, node);
  278. }
  279. return visitReturn(new Return(node,node.getInternalBody()), true);
  280. }
  281. public int makeArray(java.util.List<? extends PythonTree> nodes) throws Exception {
  282. // XXX: This should produce an array on the stack (if possible) instead of a local
  283. // the caller is responsible for freeing.
  284. int n;
  285. if (nodes == null)
  286. n = 0;
  287. else
  288. n = nodes.size();
  289. int array = code.getLocal("[Lorg/python/core/PyObject;");
  290. if (n == 0) {
  291. code.getstatic("org/python/core/Py", "EmptyObjects", $pyObjArr);
  292. code.astore(array);
  293. } else {
  294. code.iconst(n);
  295. code.anewarray("org/python/core/PyObject");
  296. code.astore(array);
  297. for(int i=0; i<n; i++) {
  298. visit(nodes.get(i));
  299. code.aload(array);
  300. code.swap();
  301. code.iconst(i);
  302. code.swap();
  303. code.aastore();
  304. }
  305. }
  306. return array;
  307. }
  308. // nulls out an array of references
  309. public void freeArray(int array) {
  310. code.aload(array);
  311. code.aconst_null();
  312. code.invokestatic("java/util/Arrays", "fill", "(" + $objArr + $obj + ")V");
  313. code.freeLocal(array);
  314. }
  315. public void getDocString(java.util.List<stmt> suite) throws Exception {
  316. if (suite.size() > 0 && suite.get(0) instanceof Expr &&
  317. ((Expr) suite.get(0)).getInternalValue() instanceof Str)
  318. {
  319. visit(((Expr) suite.get(0)).getInternalValue());
  320. } else {
  321. code.aconst_null();
  322. }
  323. }
  324. public boolean makeClosure(ScopeInfo scope) throws Exception {
  325. if (scope == null || scope.freevars == null) return false;
  326. int n = scope.freevars.size();
  327. if (n == 0) return false;
  328. int tmp = code.getLocal("[Lorg/python/core/PyObject;");
  329. code.iconst(n);
  330. code.anewarray("org/python/core/PyObject");
  331. code.astore(tmp);
  332. Map<String, SymInfo> upTbl = scope.up.tbl;
  333. for(int i=0; i<n; i++) {
  334. code.aload(tmp);
  335. code.iconst(i);
  336. loadFrame();
  337. for(int j = 1; j < scope.distance; j++) {
  338. loadf_back();
  339. }
  340. SymInfo symInfo = upTbl.get(scope.freevars.elementAt(i));
  341. code.iconst(symInfo.env_index);
  342. code.invokevirtual("org/python/core/PyFrame", "getclosure", "(I)" + $pyObj);
  343. code.aastore();
  344. }
  345. code.aload(tmp);
  346. code.freeLocal(tmp);
  347. return true;
  348. }
  349. @Override
  350. public Object visitFunctionDef(FunctionDef node) throws Exception {
  351. String name = getName(node.getInternalName());
  352. setline(node);
  353. ScopeInfo scope = module.getScopeInfo(node);
  354. // NOTE: this is attached to the constructed PyFunction, so it cannot be nulled out
  355. // with freeArray, unlike other usages of makeArray here
  356. int defaults = makeArray(scope.ac.getDefaults());
  357. code.new_("org/python/core/PyFunction");
  358. code.dup();
  359. loadFrame();
  360. code.getfield("org/python/core/PyFrame", "f_globals", $pyObj);
  361. code.aload(defaults);
  362. code.freeLocal(defaults);
  363. scope.setup_closure();
  364. scope.dump();
  365. module.PyCode(new Suite(node,node.getInternalBody()), name, true,
  366. className, false, false,
  367. node.getLine(), scope, cflags).get(code);
  368. getDocString(node.getInternalBody());
  369. if (!makeClosure(scope)) {
  370. code.invokespecial("org/python/core/PyFunction", "<init>", "(" + $pyObj + $pyObjArr + $pyCode + $pyObj + ")V");
  371. } else {
  372. code.invokespecial( "org/python/core/PyFunction", "<init>", "(" + $pyObj + $pyObjArr + $pyCode + $pyObj + $pyObjArr + ")V");
  373. }
  374. applyDecorators(node.getInternalDecorator_list());
  375. set(new Name(node,node.getInternalName(), expr_contextType.Store));
  376. return null;
  377. }
  378. private void applyDecorators(java.util.List<expr> decorators) throws Exception {
  379. if (decorators != null && !decorators.isEmpty()) {
  380. int res = storeTop();
  381. for (expr decorator : decorators) {
  382. visit(decorator); stackProduce();
  383. }
  384. for (int i = decorators.size(); i > 0; i--) {
  385. stackConsume();
  386. loadThreadState();
  387. code.aload(res);
  388. code.invokevirtual("org/python/core/PyObject", "__call__", "(" + $threadState + $pyObj + ")" + $pyObj);
  389. code.astore(res);
  390. }
  391. code.aload(res);
  392. code.freeLocal(res);
  393. }
  394. }
  395. @Override
  396. public Object visitExpr(Expr node) throws Exception {
  397. setline(node);
  398. visit(node.getInternalValue());
  399. if (print_results) {
  400. code.invokestatic("org/python/core/Py", "printResult", "(" + $pyObj + ")V");
  401. } else {
  402. code.pop();
  403. }
  404. return null;
  405. }
  406. @Override
  407. public Object visitAssign(Assign node) throws Exception {
  408. setline(node);
  409. visit(node.getInternalValue());
  410. if (node.getInternalTargets().size() == 1) {
  411. set(node.getInternalTargets().get(0));
  412. } else {
  413. int tmp = storeTop();
  414. for (expr target : node.getInternalTargets()) {
  415. set(target, tmp);
  416. }
  417. code.freeLocal(tmp);
  418. }
  419. return null;
  420. }
  421. @Override
  422. public Object visitPrint(Print node) throws Exception {
  423. setline(node);
  424. int tmp = -1;
  425. if (node.getInternalDest() != null) {
  426. visit(node.getInternalDest());
  427. tmp = storeTop();
  428. }
  429. if (node.getInternalValues() == null || node.getInternalValues().size() == 0) {
  430. if (node.getInternalDest() != null) {
  431. code.aload(tmp);
  432. code.invokestatic("org/python/core/Py", "printlnv", "(" + $pyObj + ")V");
  433. } else {
  434. code.invokestatic("org/python/core/Py", "println", "()V");
  435. }
  436. } else {
  437. for (int i = 0; i < node.getInternalValues().size(); i++) {
  438. if (node.getInternalDest() != null) {
  439. code.aload(tmp);
  440. visit(node.getInternalValues().get(i));
  441. if (node.getInternalNl() && i == node.getInternalValues().size() - 1) {
  442. code.invokestatic("org/python/core/Py", "println", "(" + $pyObj + $pyObj + ")V");
  443. } else {
  444. code.invokestatic("org/python/core/Py", "printComma", "(" + $pyObj + $pyObj + ")V");
  445. }
  446. } else {
  447. visit(node.getInternalValues().get(i));
  448. if (node.getInternalNl() && i == node.getInternalValues().size() - 1) {
  449. code.invokestatic("org/python/core/Py", "println", "(" + $pyObj + ")V");
  450. } else {
  451. code.invokestatic("org/python/core/Py", "printComma", "(" + $pyObj + ")V");
  452. }
  453. }
  454. }
  455. }
  456. if (node.getInternalDest() != null) {
  457. code.freeLocal(tmp);
  458. }
  459. return null;
  460. }
  461. @Override
  462. public Object visitDelete(Delete node) throws Exception {
  463. setline(node);
  464. traverse(node);
  465. return null;
  466. }
  467. @Override
  468. public Object visitPass(Pass node) throws Exception {
  469. setline(node);
  470. return null;
  471. }
  472. @Override
  473. public Object visitBreak(Break node) throws Exception {
  474. //setline(node); Not needed here...
  475. if (breakLabels.empty()) {
  476. throw new ParseException("'break' outside loop", node);
  477. }
  478. doFinallysDownTo(bcfLevel);
  479. code.goto_((Label)breakLabels.peek());
  480. return null;
  481. }
  482. @Override
  483. public Object visitContinue(Continue node) throws Exception {
  484. //setline(node); Not needed here...
  485. if (continueLabels.empty()) {
  486. throw new ParseException("'continue' not properly in loop", node);
  487. }
  488. doFinallysDownTo(bcfLevel);
  489. code.goto_((Label)continueLabels.peek());
  490. return Exit;
  491. }
  492. @Override
  493. public Object visitYield(Yield node) throws Exception {
  494. setline(node);
  495. if (!fast_locals) {
  496. throw new ParseException("'yield' outside function", node);
  497. }
  498. int stackState = saveStack();
  499. if (node.getInternalValue() != null) {
  500. visit(node.getInternalValue());
  501. } else {
  502. getNone();
  503. }
  504. setLastI(++yield_count);
  505. saveLocals();
  506. code.areturn();
  507. Label restart = new Label();
  508. yields.addElement(restart);
  509. code.label(restart);
  510. restoreLocals();
  511. restoreStack(stackState);
  512. loadFrame();
  513. code.invokevirtual("org/python/core/PyFrame", "getGeneratorInput", "()" + $obj);
  514. code.dup();
  515. code.instanceof_("org/python/core/PyException");
  516. Label done2 = new Label();
  517. code.ifeq(done2);
  518. code.checkcast("java/lang/Throwable");
  519. code.athrow();
  520. code.label(done2);
  521. code.checkcast("org/python/core/PyObject");
  522. return null;
  523. }
  524. private void stackProduce() {
  525. stackProduce("org/python/core/PyObject");
  526. }
  527. private void stackProduce(String signature) {
  528. stack.push(signature);
  529. }
  530. private void stackConsume() {
  531. stackConsume(1);
  532. }
  533. private void stackConsume(int numItems) {
  534. for (int i = 0; i < numItems; i++) {
  535. stack.pop();
  536. }
  537. }
  538. private int saveStack() throws Exception {
  539. if (stack.size() > 0) {
  540. int array = code.getLocal("[Ljava/lang/Object;");
  541. code.iconst(stack.size());
  542. code.anewarray("java/lang/Object");
  543. code.astore(array);
  544. for (int i = 0; i < stack.size(); i++) {
  545. code.aload(array);
  546. // Stack: |- ... value array
  547. code.swap();
  548. code.iconst(i);
  549. code.swap();
  550. // Stack: |- ... array index value
  551. code.aastore();
  552. // Stack: |- ...
  553. }
  554. return array;
  555. } else {
  556. return -1;
  557. }
  558. }
  559. private void restoreStack(int array) throws Exception {
  560. if (stack.size() > 0) {
  561. int i = stack.size() -1;
  562. for (String signature : stack) {
  563. code.aload(array);
  564. // Stack: |- ... array
  565. code.iconst(i);
  566. code.aaload();
  567. // Stack: |- ... value
  568. code.checkcast(signature);
  569. }
  570. code.freeLocal(array);
  571. }
  572. }
  573. private void restoreLocals() throws Exception {
  574. endExceptionHandlers();
  575. Vector v = code.getActiveLocals();
  576. loadFrame();
  577. code.getfield("org/python/core/PyFrame", "f_savedlocals", "[Ljava/lang/Object;");
  578. int locals = code.getLocal("[Ljava/lang/Object;");
  579. code.astore(locals);
  580. for (int i = 0; i < v.size(); i++) {
  581. String type = (String) v.elementAt(i);
  582. if (type == null)
  583. continue;
  584. code.aload(locals);
  585. code.iconst(i);
  586. code.aaload();
  587. code.checkcast(type);
  588. code.astore(i);
  589. }
  590. code.freeLocal(locals);
  591. restartExceptionHandlers();
  592. }
  593. /**
  594. * Close all the open exception handler ranges. This should be paired
  595. * with restartExceptionHandlers to delimit internal code that
  596. * shouldn't be handled by user handlers. This allows us to set
  597. * variables without the verifier thinking we might jump out of our
  598. * handling with an exception.
  599. */
  600. private void endExceptionHandlers()
  601. {
  602. Label end = new Label();
  603. code.label(end);
  604. for (int i = 0; i < exceptionHandlers.size(); ++i) {
  605. ExceptionHandler handler =
  606. (ExceptionHandler)exceptionHandlers.elementAt(i);
  607. handler.exceptionEnds.addElement(end);
  608. }
  609. }
  610. private void restartExceptionHandlers()
  611. {
  612. Label start = new Label();
  613. code.label(start);
  614. for (int i = 0; i < exceptionHandlers.size(); ++i) {
  615. ExceptionHandler handler =
  616. (ExceptionHandler)exceptionHandlers.elementAt(i);
  617. handler.exceptionStarts.addElement(start);
  618. }
  619. }
  620. private void saveLocals() throws Exception {
  621. Vector v = code.getActiveLocals();
  622. code.iconst(v.size());
  623. code.anewarray("java/lang/Object");
  624. int locals = code.getLocal("[Ljava/lang/Object;");
  625. code.astore(locals);
  626. for (int i = 0; i < v.size(); i++) {
  627. String type = (String) v.elementAt(i);
  628. if (type == null)
  629. continue;
  630. code.aload(locals);
  631. code.iconst(i);
  632. //code.checkcast(code.pool.Class("java/lang/Object"));
  633. if (i == 2222) {
  634. code.aconst_null();
  635. } else
  636. code.aload(i);
  637. code.aastore();
  638. }
  639. loadFrame();
  640. code.aload(locals);
  641. code.putfield("org/python/core/PyFrame", "f_savedlocals", "[Ljava/lang/Object;");
  642. code.freeLocal(locals);
  643. }
  644. @Override
  645. public Object visitReturn(Return node) throws Exception {
  646. return visitReturn(node, false);
  647. }
  648. public Object visitReturn(Return node, boolean inEval) throws Exception {
  649. setline(node);
  650. if (!inEval && !fast_locals) {
  651. throw new ParseException("'return' outside function", node);
  652. }
  653. int tmp = 0;
  654. if (node.getInternalValue() != null) {
  655. if (my_scope.generator)
  656. throw new ParseException("'return' with argument " +
  657. "inside generator", node);
  658. visit(node.getInternalValue());
  659. tmp = code.getReturnLocal();
  660. code.astore(tmp);
  661. }
  662. doFinallysDownTo(0);
  663. setLastI(-1);
  664. if (node.getInternalValue() != null) {
  665. code.aload(tmp);
  666. } else {
  667. getNone();
  668. }
  669. code.areturn();
  670. return Exit;
  671. }
  672. @Override
  673. public Object visitRaise(Raise node) throws Exception {
  674. setline(node);
  675. if (node.getInternalType() != null) { visit(node.getInternalType()); stackProduce(); }
  676. if (node.getInternalInst() != null) { visit(node.getInternalInst()); stackProduce(); }
  677. if (node.getInternalTback() != null) { visit(node.getInternalTback()); stackProduce(); }
  678. if (node.getInternalType() == null) {
  679. code.invokestatic("org/python/core/Py", "makeException", "()" + $pyExc);
  680. } else if (node.getInternalInst() == null) {
  681. stackConsume();
  682. code.invokestatic("org/python/core/Py", "makeException", "(" + $pyObj + ")" + $pyExc);
  683. } else if (node.getInternalTback() == null) {
  684. stackConsume(2);
  685. code.invokestatic("org/python/core/Py", "makeException", "(" + $pyObj + $pyObj + ")" + $pyExc);
  686. } else {
  687. stackConsume(3);
  688. code.invokestatic("org/python/core/Py", "makeException", "(" + $pyObj + $pyObj + $pyObj + ")" + $pyExc);
  689. }
  690. code.athrow();
  691. return Exit;
  692. }
  693. @Override
  694. public Object visitImport(Import node) throws Exception {
  695. setline(node);
  696. for (alias a : node.getInternalNames()) {
  697. String asname = null;
  698. if (a.getInternalAsname() != null) {
  699. String name = a.getInternalName();
  700. asname = a.getInternalAsname();
  701. code.ldc(name);
  702. loadFrame();
  703. code.invokestatic("org/python/core/imp", "importOneAs", "(" + $str + $pyFrame + ")" + $pyObj);
  704. } else {
  705. String name = a.getInternalName();
  706. asname = name;
  707. if (asname.indexOf('.') > 0)
  708. asname = asname.substring(0, asname.indexOf('.'));
  709. code.ldc(name);
  710. loadFrame();
  711. code.invokestatic("org/python/core/imp", "importOne", "(" + $str + $pyFrame + ")" + $pyObj);
  712. }
  713. set(new Name(a, asname, expr_contextType.Store));
  714. }
  715. return null;
  716. }
  717. @Override
  718. public Object visitImportFrom(ImportFrom node) throws Exception {
  719. Future.checkFromFuture(node); // future stmt support
  720. setline(node);
  721. code.ldc(node.getInternalModule());
  722. java.util.List<alias> names = node.getInternalNames();
  723. if (names == null || names.size() == 0) {
  724. throw new ParseException("Internel parser error", node);
  725. } else if (names.size() == 1 && names.get(0).getInternalName().equals("*")) {
  726. if (node.getInternalLevel() > 0) {
  727. throw new ParseException("'import *' not allowed with 'from .'", node);
  728. }
  729. if (my_scope.func_level > 0) {
  730. module.error("import * only allowed at module level", false, node);
  731. if (my_scope.contains_ns_free_vars) {
  732. module.error("import * is not allowed in function '" +
  733. my_scope.scope_name +
  734. "' because it contains a nested function with free variables",
  735. true, node);
  736. }
  737. }
  738. if (my_scope.func_level > 1) {
  739. module.error("import * is not allowed in function '" +
  740. my_scope.scope_name +
  741. "' because it is a nested function",
  742. true, node);
  743. }
  744. loadFrame();
  745. code.invokestatic("org/python/core/imp", "importAll", "(" + $str + $pyFrame + ")V");
  746. } else {
  747. java.util.List<String> fromNames = new ArrayList<String>();//[names.size()];
  748. java.util.List<String> asnames = new ArrayList<String>();//[names.size()];
  749. for (int i = 0; i < names.size(); i++) {
  750. fromNames.add(names.get(i).getInternalName());
  751. asnames.add(names.get(i).getInternalAsname());
  752. if (asnames.get(i) == null)
  753. asnames.set(i, fromNames.get(i));
  754. }
  755. int strArray = makeStrings(code, fromNames);
  756. code.aload(strArray);
  757. code.freeLocal(strArray);
  758. loadFrame();
  759. if (node.getInternalLevel() == 0) {
  760. if (module.getFutures().isAbsoluteImportOn()) {
  761. code.iconst_0();
  762. } else {
  763. code.iconst_m1();
  764. }
  765. } else {
  766. code.iconst(node.getInternalLevel());
  767. }
  768. code.invokestatic("org/python/core/imp", "importFrom", "(" + $str + $strArr + $pyFrame + "I" + ")" + $pyObjArr);
  769. int tmp = storeTop();
  770. for (int i = 0; i < names.size(); i++) {
  771. code.aload(tmp);
  772. code.iconst(i);
  773. code.aaload();
  774. set(new Name(names.get(i), asnames.get(i), expr_contextType.Store));
  775. }
  776. code.freeLocal(tmp);
  777. }
  778. return null;
  779. }
  780. @Override
  781. public Object visitGlobal(Global node) throws Exception {
  782. return null;
  783. }
  784. @Override
  785. public Object visitExec(Exec node) throws Exception {
  786. setline(node);
  787. visit(node.getInternalBody());
  788. stackProduce();
  789. if (node.getInternalGlobals() != null) {
  790. visit(node.getInternalGlobals());
  791. } else {
  792. code.aconst_null();
  793. }
  794. stackProduce();
  795. if (node.getInternalLocals() != null) {
  796. visit(node.getInternalLocals());
  797. } else {
  798. code.aconst_null();
  799. }
  800. stackProduce();
  801. //do the real work here
  802. stackConsume(3);
  803. code.invokestatic("org/python/core/Py", "exec", "(" + $pyObj + $pyObj + $pyObj + ")V");
  804. return null;
  805. }
  806. @Override
  807. public Object visitAssert(Assert node) throws Exception {
  808. setline(node);
  809. Label end_of_assert = new Label();
  810. /* First do an if __debug__: */
  811. loadFrame();
  812. emitGetGlobal("__debug__");
  813. code.invokevirtual("org/python/core/PyObject", "__nonzero__", "()Z");
  814. code.ifeq(end_of_assert);
  815. /* Now do the body of the assert. If PyObject.__nonzero__ is true,
  816. then the assertion succeeded, the message portion should not be
  817. processed. Otherwise, the message will be processed. */
  818. visit(node.getInternalTest());
  819. code.invokevirtual("org/python/core/PyObject", "__nonzero__", "()Z");
  820. /* If evaluation is false, then branch to end of method */
  821. code.ifne(end_of_assert);
  822. /* Visit the message part of the assertion, or pass Py.None */
  823. if( node.getInternalMsg() != null ) {
  824. visit(node.getInternalMsg());
  825. } else {
  826. getNone();
  827. }
  828. /* Push exception type onto stack(Py.AssertionError) */
  829. code.getstatic("org/python/core/Py", "AssertionError", "Lorg/python/core/PyObject;");
  830. code.swap(); // The type is the first argument, but the message could be a yield
  831. code.invokestatic("org/python/core/Py", "makeException", "(" + $pyObj + $pyObj + ")" + $pyExc);
  832. /* Raise assertion error. Only executes this logic if assertion
  833. failed */
  834. code.athrow();
  835. /* And finally set the label for the end of it all */
  836. code.label(end_of_assert);
  837. return null;
  838. }
  839. public Object doTest(Label end_of_if, If node, int index)
  840. throws Exception
  841. {
  842. Label end_of_suite = new Label();
  843. setline(node.getInternalTest());
  844. visit(node.getInternalTest());
  845. code.invokevirtual("org/python/core/PyObject", "__nonzero__", "()Z");
  846. code.ifeq(end_of_suite);
  847. Object exit = suite(node.getInternalBody());
  848. if (end_of_if != null && exit == null)
  849. code.goto_(end_of_if);
  850. code.label(end_of_suite);
  851. if (node.getInternalOrelse() != null) {
  852. return suite(node.getInternalOrelse()) != null ? exit : null;
  853. } else {
  854. return null;
  855. }
  856. }
  857. @Override
  858. public Object visitIf(If node) throws Exception {
  859. Label end_of_if = null;
  860. if (node.getInternalOrelse() != null)
  861. end_of_if = new Label();
  862. Object exit = doTest(end_of_if, node, 0);
  863. if (end_of_if != null)
  864. code.label(end_of_if);
  865. return exit;
  866. }
  867. @Override
  868. public Object visitIfExp(IfExp node) throws Exception {
  869. setline(node.getInternalTest());
  870. Label end = new Label();
  871. Label end_of_else = new Label();
  872. visit(node.getInternalTest());
  873. code.invokevirtual("org/python/core/PyObject", "__nonzero__", "()Z");
  874. code.ifeq(end_of_else);
  875. visit(node.getInternalBody());
  876. code.goto_(end);
  877. code.label(end_of_else);
  878. visit(node.getInternalOrelse());
  879. code.label(end);
  880. return null;
  881. }
  882. public int beginLoop() {
  883. continueLabels.push(new Label());
  884. breakLabels.push(new Label());
  885. int savebcf = bcfLevel;
  886. bcfLevel = exceptionHandlers.size();
  887. return savebcf;
  888. }
  889. public void finishLoop(int savebcf) {
  890. continueLabels.pop();
  891. breakLabels.pop();
  892. bcfLevel = savebcf;
  893. }
  894. @Override
  895. public Object visitWhile(While node) throws Exception {
  896. int savebcf = beginLoop();
  897. Label continue_loop = (Label)continueLabels.peek();
  898. Label break_loop = (Label)breakLabels.peek();
  899. Label start_loop = new Label();
  900. code.goto_(continue_loop);
  901. code.label(start_loop);
  902. //Do suite
  903. suite(node.getInternalBody());
  904. code.label(continue_loop);
  905. setline(node);
  906. //Do test
  907. visit(node.getInternalTest());
  908. code.invokevirtual("org/python/core/PyObject", "__nonzero__", "()Z");
  909. code.ifne(start_loop);
  910. finishLoop(savebcf);
  911. if (node.getInternalOrelse() != null) {
  912. //Do else
  913. suite(node.getInternalOrelse());
  914. }
  915. code.label(break_loop);
  916. // Probably need to detect "guaranteed exits"
  917. return null;
  918. }
  919. @Override
  920. public Object visitFor(For node) throws Exception {
  921. int savebcf = beginLoop();
  922. Label continue_loop = (Label)continueLabels.peek();
  923. Label break_loop = (Label)breakLabels.peek();
  924. Label start_loop = new Label();
  925. Label next_loop = new Label();
  926. int iter_tmp = code.getLocal("org/python/core/PyObject");
  927. int expr_tmp = code.getLocal("org/python/core/PyObject");
  928. setline(node);
  929. //parse the list
  930. visit(node.getInternalIter());
  931. //set up the loop iterator
  932. code.invokevirtual("org/python/core/PyObject", "__iter__", "()Lorg/python/core/PyObject;");
  933. code.astore(iter_tmp);
  934. //do check at end of loop. Saves one opcode ;-)
  935. code.goto_(next_loop);
  936. code.label(start_loop);
  937. //set iter variable to current entry in list
  938. set(node.getInternalTarget(), expr_tmp);
  939. //evaluate for body
  940. suite(node.getInternalBody());
  941. code.label(continue_loop);
  942. code.label(next_loop);
  943. setline(node);
  944. //get the next element from the list
  945. code.aload(iter_tmp);
  946. code.invokevirtual("org/python/core/PyObject", "__iternext__", "()" + $pyObj);
  947. code.astore(expr_tmp);
  948. code.aload(expr_tmp);
  949. //if no more elements then fall through
  950. code.ifnonnull(start_loop);
  951. finishLoop(savebcf);
  952. if (node.getInternalOrelse() != null) {
  953. //Do else clause if provided
  954. suite(node.getInternalOrelse());
  955. }
  956. code.label(break_loop);
  957. code.freeLocal(iter_tmp);
  958. code.freeLocal(expr_tmp);
  959. // Probably need to detect "guaranteed exits"
  960. return null;
  961. }
  962. public void exceptionTest(int exc, Label end_of_exceptions,
  963. TryExcept node, int index)
  964. throws Exception
  965. {
  966. for (int i = 0; i < node.getInternalHandlers().size(); i++) {
  967. ExceptHandler handler = (ExceptHandler)node.getInternalHandlers().get(i);
  968. //setline(name);
  969. Label end_of_self = new Label();
  970. if (handler.getInternalType() != null) {
  971. code.aload(exc);
  972. //get specific exception
  973. visit(handler.getInternalType());
  974. code.invokevirtual("org/python/core/PyException", "match", "(" + $pyObj + ")Z");
  975. code.ifeq(end_of_self);
  976. } else {
  977. if (i != node.getInternalHandlers().size()-1) {
  978. throw new ParseException(
  979. "default 'except:' must be last", handler);
  980. }
  981. }
  982. if (handler.getInternalName() != null) {
  983. code.aload(exc);
  984. code.getfield("org/python/core/PyException", "value", "Lorg/python/core/PyObject;");
  985. set(handler.getInternalName());
  986. }
  987. //do exception body
  988. suite(handler.getInternalBody());
  989. code.goto_(end_of_exceptions);
  990. code.label(end_of_self);
  991. }
  992. code.aload(exc);
  993. code.athrow();
  994. }
  995. @Override
  996. public Object visitTryFinally(TryFinally node) throws Exception
  997. {
  998. Label start = new Label();
  999. Label end = new Label();
  1000. Label handlerStart = new Label();
  1001. Label finallyEnd = new Label();
  1002. Object ret;
  1003. ExceptionHandler inFinally = new ExceptionHandler(node);
  1004. // Do protected suite
  1005. exceptionHandlers.push(inFinally);
  1006. int excLocal = code.getLocal("java/lang/Throwable");
  1007. code.aconst_null();
  1008. code.astore(excLocal);
  1009. code.label(start);
  1010. inFinally.exceptionStarts.addElement(start);
  1011. ret = suite(node.getInternalBody());
  1012. code.label(end);
  1013. inFinally.exceptionEnds.addElement(end);
  1014. inFinally.bodyDone = true;
  1015. exceptionHandlers.pop();
  1016. if (ret == NoExit) {
  1017. inlineFinally(inFinally);
  1018. code.goto_(finallyEnd);
  1019. }
  1020. // Handle any exceptions that get thrown in suite
  1021. code.label(handlerStart);
  1022. code.astore(excLocal);
  1023. code.aload(excLocal);
  1024. loadFrame();
  1025. code.invokestatic("org/python/core/Py", "addTraceback", "(" + $throwable + $pyFrame + ")V");
  1026. inlineFinally(inFinally);
  1027. code.aload(excLocal);
  1028. code.checkcast("java/lang/Throwable");
  1029. code.athrow();
  1030. code.label(finallyEnd);
  1031. code.freeLocal(excLocal);
  1032. inFinally.addExceptionHandlers(handlerStart);
  1033. // According to any JVM verifiers, this code block might not return
  1034. return null;
  1035. }
  1036. private void inlineFinally(ExceptionHandler handler) throws Exception {
  1037. if (!handler.bodyDone) {
  1038. // end the previous exception block so inlined finally code doesn't
  1039. // get covered by our exception handler.
  1040. Label end = new Label();
  1041. code.label(end);
  1042. handler.exceptionEnds.addElement(end);
  1043. // also exiting the try: portion of this particular finally
  1044. }
  1045. if (handler.isFinallyHandler()) {
  1046. handler.finalBody(this);
  1047. }
  1048. }
  1049. private void reenterProtectedBody(ExceptionHandler handler) throws Exception {
  1050. // restart exception coverage
  1051. Label restart = new Label();
  1052. code.label(restart);
  1053. handler.exceptionStarts.addElement(restart);
  1054. }
  1055. /**
  1056. * Inline the finally handling code for levels down to the levelth parent
  1057. * (0 means all). This takes care to avoid having more nested finallys
  1058. * catch exceptions throw by the parent finally code. This also pops off
  1059. * all the handlers above level temporarily.
  1060. */
  1061. private void doFinallysDownTo(int level) throws Exception {
  1062. Stack poppedHandlers = new Stack();
  1063. while (exceptionHandlers.size() > level) {
  1064. ExceptionHandler handler =
  1065. (ExceptionHandler)exceptionHandlers.pop();
  1066. inlineFinally(handler);
  1067. poppedHandlers.push(handler);
  1068. }
  1069. while (poppedHandlers.size() > 0) {
  1070. ExceptionHandler handler =
  1071. (ExceptionHandler)poppedHandlers.pop();
  1072. reenterProtectedBody(handler);
  1073. exceptionHandlers.push(handler);
  1074. }
  1075. }
  1076. @Override
  1077. public Object visitTryExcept(TryExcept node) throws Exception {
  1078. Label start = new Label();
  1079. Label end = new Label();
  1080. Label handler_start = new Label();
  1081. Label handler_end = new Label();
  1082. ExceptionHandler handler = new ExceptionHandler();
  1083. code.label(start);
  1084. handler.exceptionStarts.addElement(start);
  1085. exceptionHandlers.push(handler);
  1086. //Do suite
  1087. Object exit = suite(node.getInternalBody());
  1088. exceptionHandlers.pop();
  1089. code.label(end);
  1090. handler.exceptionEnds.addElement(end);
  1091. if (exit == null)
  1092. code.goto_(handler_end);
  1093. code.label(handler_start);
  1094. loadFrame();
  1095. code.invokestatic("org/python/core/Py", "setException", "(" + $throwable + $pyFrame + ")" + $pyExc);
  1096. int exc = code.getFinallyLocal("java/lang/Throwable");
  1097. code.astore(exc);
  1098. if (node.getInternalOrelse() == null) {
  1099. //No else clause to worry about
  1100. exceptionTest(exc, handler_end, node, 1);
  1101. code.label(handler_end);
  1102. } else {
  1103. //Have else clause
  1104. Label else_end = new Label();
  1105. exceptionTest(exc, else_end, node, 1);
  1106. code.label(handler_end);
  1107. //do else clause
  1108. suite(node.getInternalOrelse());
  1109. code.label(else_end);
  1110. }
  1111. code.freeFinallyLocal(exc);
  1112. handler.addExceptionHandlers(handler_start);
  1113. return null;
  1114. }
  1115. @Override
  1116. public Object visitSuite(Suite node) throws Exception {
  1117. return suite(node.getInternalBody());
  1118. }
  1119. public Object suite(java.util.List<stmt> stmts) throws Exception {
  1120. for(stmt s: stmts) {
  1121. Object exit = visit(s);
  1122. if (exit != null)
  1123. return Exit;
  1124. }
  1125. return null;
  1126. }
  1127. @Override
  1128. public Object visitBoolOp(BoolOp node) throws Exception {
  1129. Label end = new Label();
  1130. visit(node.getInternalValues().get(0));
  1131. for (int i = 1; i < node.getInternalValues().size(); i++) {
  1132. code.dup();
  1133. code.invokevirtual("org/python/core/PyObject", "__nonzero__", "()Z");
  1134. switch (node.getInternalOp()) {
  1135. case Or :
  1136. code.ifne(end);
  1137. break;
  1138. case And :
  1139. code.ifeq(end);
  1140. break;
  1141. }
  1142. code.pop();
  1143. visit(node.getInternalValues().get(i));
  1144. }
  1145. code.label(end);
  1146. return null;
  1147. }
  1148. @Override
  1149. public Object visitCompare(Compare node) throws Exception {
  1150. int last = code.getLocal("org/python/core/PyObject");
  1151. int result = code.getLocal("org/python/core/PyObject");
  1152. Label end = new Label();
  1153. visit(node.getInternalLeft());
  1154. code.astore(last);
  1155. int n = node.getInternalOps().size();
  1156. for(int i = 0; i < n - 1; i++) {
  1157. visit(node.getInternalComparators().get(i));
  1158. code.aload(last);
  1159. code.swap();
  1160. code.dup();
  1161. code.astore(last);
  1162. visitCmpop(node.getInternalOps().get(i));
  1163. code.dup();
  1164. code.astore(result);
  1165. code.invokevirtual("org/python/core/PyObject", "__nonzero__", "()Z");
  1166. code.ifeq(end);
  1167. }
  1168. visit(node.getInternalComparators().get(n-1));
  1169. code.aload(last);
  1170. code.swap();
  1171. visitCmpop(node.getInternalOps().get(n-1));
  1172. if (n > 1) {
  1173. code.astore(result);
  1174. code.label(end);
  1175. code.aload(result);
  1176. }
  1177. code.aconst_null();
  1178. code.astore(last);
  1179. code.freeLocal(last);
  1180. code.freeLocal(result);
  1181. return null;
  1182. }
  1183. public void visitCmpop(cmpopType op) throws Exception {
  1184. String name = null;
  1185. switch (op) {
  1186. case Eq: name = "_eq"; break;
  1187. case NotEq: name = "_ne"; break;
  1188. case Lt: name = "_lt"; break;
  1189. case LtE: name = "_le"; break;
  1190. case Gt: name = "_gt"; break;
  1191. case GtE: name = "_ge"; break;
  1192. case Is: name = "_is"; break;
  1193. case IsNot: name = "_isnot"; break;
  1194. case In: name = "_in"; break;
  1195. case NotIn: name = "_notin"; break;
  1196. }
  1197. code.invokevirtual("org/python/core/PyObject", name, "(" + $pyObj + ")" + $pyObj);
  1198. }
  1199. @Override
  1200. public Object visitBinOp(BinOp node) throws Exception {
  1201. visit(node.getInternalLeft());
  1202. stackProduce();
  1203. visit(node.getInternalRight());
  1204. stackConsume();
  1205. String name = null;
  1206. switch (node.getInternalOp()) {
  1207. case Add: name = "_add"; break;
  1208. case Sub: name = "_sub"; break;
  1209. case Mult: name = "_mul"; break;
  1210. case Div: name = "_div"; break;
  1211. case Mod: name = "_mod"; break;
  1212. case Pow: name = "_pow"; break;
  1213. case LShift: name = "_lshift"; break;
  1214. case RShift: name = "_rshift"; break;
  1215. case BitOr: name = "_or"; break;
  1216. case BitXor: name = "_xor"; break;
  1217. case BitAnd: name = "_and"; break;
  1218. case FloorDiv: name = "_floordiv"; break;
  1219. }
  1220. if (node.getInternalOp() == operatorType.Div && module.getFutures().areDivisionOn()) {
  1221. name = "_truediv";
  1222. }
  1223. code.invokevirtual("org/python/core/PyObject", name, "(" + $pyObj + ")" + $pyObj);
  1224. return null;
  1225. }
  1226. @Override
  1227. public Object visitUnaryOp(UnaryOp node) throws Exception {
  1228. visit(node.getInternalOperand());
  1229. String name = null;
  1230. switch (node.getInternalOp()) {
  1231. case Invert: name = "__invert__"; break;
  1232. case Not: name = "__not__"; break;
  1233. case UAdd: name = "__pos__"; break;
  1234. case USub: name = "__neg__"; break;
  1235. }
  1236. code.invokevirtual("org/python/core/PyObject", name, "()" + $pyObj);
  1237. return null;
  1238. }
  1239. @Override
  1240. public Object visitAugAssign(AugAssign node) throws Exception {
  1241. setline(node);
  1242. augmode = expr_contextType.Load;
  1243. visit(node.getInternalTarget());
  1244. int target = storeTop();
  1245. visit(node.getInternalValue());
  1246. code.aload(target);
  1247. code.swap();
  1248. String name = null;
  1249. switch (node.getInternalOp()) {
  1250. case Add: name = "_iadd"; break;
  1251. case Sub: name = "_isub"; break;
  1252. case Mult: name = "_imul"; break;
  1253. case Div: name = "_idiv"; break;
  1254. case Mod: name = "_imod"; break;
  1255. case Pow: name = "_ipow"; break;
  1256. case LShift: name = "_ilshift"; break;
  1257. case RShift: name = "_irshift"; break;
  1258. case BitOr: name = "_ior"; break;
  1259. case BitXor: name = "_ixor"; break;
  1260. case BitAnd: name = "_iand"; break;
  1261. case FloorDiv: name = "_ifloordiv"; break;
  1262. }
  1263. if (node.getInternalOp() == operatorType.Div && module.getFutures().areDivisionOn()) {
  1264. name = "_itruediv";
  1265. }
  1266. code.invokevirtual("org/python/core/PyObject", name, "(" + $pyObj + ")" + $pyObj);
  1267. code.freeLocal(target);
  1268. temporary = storeTop();
  1269. augmode = expr_contextType.Store;
  1270. visit(node.getInternalTarget());
  1271. code.freeLocal(temporary);
  1272. return null;
  1273. }
  1274. public static int makeStrings(Code c, Collection<String> names)
  1275. throws IOException
  1276. {
  1277. if (names != null) {
  1278. c.iconst(names.size());
  1279. } else {
  1280. c.iconst_0();
  1281. }
  1282. c.anewarray("java/lang/String");
  1283. int strings = c.getLocal("[Ljava/lang/String;");
  1284. c.astore(strings);
  1285. if (names != null) {
  1286. int i = 0;
  1287. for (String name : names) {
  1288. c.aload(strings);
  1289. c.iconst(i);
  1290. c.ldc(name);
  1291. c.aastore();
  1292. i++;
  1293. }
  1294. }
  1295. return strings;
  1296. }
  1297. public Object invokeNoKeywords(Attribute node, java.util.List<expr> values)
  1298. throws Exception
  1299. {
  1300. String name = getName(node.getInternalAttr());
  1301. visit(node.getInternalValue()); stackProduce();
  1302. code.ldc(name);
  1303. code.invokevirtual("org/python/core/PyObject", "__getattr__", "(" + $str + ")" + $pyObj);
  1304. loadThreadState(); stackProduce("org/python/core/ThreadState");
  1305. switch (values.size()) {
  1306. case 0:
  1307. stackConsume(2); // target + ts
  1308. code.invokevirtual("org/python/core/PyObject", "__call__", "(" + $threadState + ")" + $pyObj);
  1309. break;
  1310. case 1:
  1311. visit(values.get(0));
  1312. stackConsume(2); // target + ts
  1313. code.invokevirtual("org/python/core/PyObject", "__call__", "(" + $threadState + $pyObj + ")" + $pyObj);
  1314. break;
  1315. case 2:
  1316. visit(values.get(0)); stackProduce();
  1317. visit(values.get(1)

Large files files are truncated, but you can click here to view the full file