|
51 | 51 | import com.oracle.graal.python.builtins.objects.cext.CExtNodesFactory.AsLongNodeGen;
|
52 | 52 | import com.oracle.graal.python.builtins.objects.cext.CExtNodesFactory.AsPythonObjectNodeGen;
|
53 | 53 | import com.oracle.graal.python.builtins.objects.cext.CExtNodesFactory.CextUpcallNodeGen;
|
| 54 | +import com.oracle.graal.python.builtins.objects.cext.CExtNodesFactory.GetNativeClassNodeGen; |
54 | 55 | import com.oracle.graal.python.builtins.objects.cext.CExtNodesFactory.ObjectUpcallNodeGen;
|
55 | 56 | import com.oracle.graal.python.builtins.objects.cext.CExtNodesFactory.ToJavaNodeGen;
|
56 | 57 | import com.oracle.graal.python.builtins.objects.cext.CExtNodesFactory.ToSulongNodeGen;
|
@@ -535,14 +536,28 @@ public static FromCharPointerNode create() {
|
535 | 536 | }
|
536 | 537 | }
|
537 | 538 |
|
538 |
| - public static class GetNativeClassNode extends CExtBaseNode { |
| 539 | + public abstract static class GetNativeClassNode extends CExtBaseNode { |
539 | 540 |
|
540 | 541 | @Child PCallNativeNode callGetObTypeNode;
|
541 | 542 | @Child ToJavaNode toJavaNode;
|
542 | 543 |
|
543 | 544 | @CompilationFinal private TruffleObject func;
|
544 | 545 |
|
545 |
| - public PythonClass execute(PythonNativeObject object) { |
| 546 | + public abstract PythonClass execute(PythonNativeObject object); |
| 547 | + |
| 548 | + @Specialization(guards = "object == cachedObject", limit = "1") |
| 549 | + PythonClass getNativeClassCached(@SuppressWarnings("unused") PythonNativeObject object, |
| 550 | + @SuppressWarnings("unused") @Cached("object") PythonNativeObject cachedObject, |
| 551 | + @Cached("getNativeClass(cachedObject)") PythonClass cachedClass) { |
| 552 | + // TODO: (tfel) is this really something we can do? It's so rare for this class to |
| 553 | + // change that it shouldn't be worth the effort, but in native code, anything can |
| 554 | + // happen. OTOH, CPython also has caches that can become invalid when someone just goes |
| 555 | + // and changes the ob_type of an object. |
| 556 | + return cachedClass; |
| 557 | + } |
| 558 | + |
| 559 | + @Specialization |
| 560 | + PythonClass getNativeClass(PythonNativeObject object) { |
546 | 561 | // do not convert wrap 'object.object' since that is really the native pointer object
|
547 | 562 | Object[] args = new Object[]{object.object};
|
548 | 563 | return (PythonClass) getToJavaNode().execute(getCallGetObTypeNode().execute(getObTypeFunction(), args));
|
@@ -573,7 +588,7 @@ TruffleObject getObTypeFunction() {
|
573 | 588 | }
|
574 | 589 |
|
575 | 590 | public static GetNativeClassNode create() {
|
576 |
| - return new GetNativeClassNode(); |
| 591 | + return GetNativeClassNodeGen.create(); |
577 | 592 | }
|
578 | 593 | }
|
579 | 594 |
|
|
0 commit comments