Skip to content

Commit be9ab6d

Browse files
committed
Fix: message PythonNativeWrapperLibrary.isNative/getNativePointer did not consider assumption.
1 parent c8e7bbe commit be9ab6d

File tree

3 files changed

+42
-12
lines changed

3 files changed

+42
-12
lines changed

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/builtins/objects/PythonAbstractObject.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,7 @@
7979
import com.oracle.graal.python.builtins.objects.bytes.PBytes;
8080
import com.oracle.graal.python.builtins.objects.cext.CApiGuards;
8181
import com.oracle.graal.python.builtins.objects.cext.DynamicObjectNativeWrapper;
82+
import com.oracle.graal.python.builtins.objects.cext.PythonNativeWrapper;
8283
import com.oracle.graal.python.builtins.objects.common.SequenceNodes;
8384
import com.oracle.graal.python.builtins.objects.dict.PDict;
8485
import com.oracle.graal.python.builtins.objects.function.PArguments;
@@ -134,6 +135,7 @@
134135
import com.oracle.graal.python.runtime.PythonOptions;
135136
import com.oracle.graal.python.runtime.exception.PException;
136137
import com.oracle.graal.python.util.OverflowException;
138+
import com.oracle.truffle.api.Assumption;
137139
import com.oracle.truffle.api.CompilerDirectives;
138140
import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary;
139141
import com.oracle.truffle.api.TruffleLanguage;
@@ -186,7 +188,7 @@ public final void clearNativeWrapper(ConditionProfile hasHandleValidAssumptionPr
186188
// The null check is important because it might be that we actually never got a to-native
187189
// message but still modified the reference count.
188190
if (hasHandleValidAssumptionProfile.profile(nativeWrapper != null && nativeWrapper.getHandleValidAssumption() != null)) {
189-
nativeWrapper.getHandleValidAssumption().invalidate("releasing handle for native wrapper");
191+
PythonNativeWrapper.invalidateAssumption(nativeWrapper.getHandleValidAssumption());
190192
}
191193
nativeWrapper = null;
192194
}

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/builtins/objects/cext/CExtNodes.java

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3054,7 +3054,7 @@ static void doPrimitiveNativeWrapper(@SuppressWarnings("unused") Object delegate
30543054
assert !isSmallIntegerWrapperSingleton(contextRef, nativeWrapper) : "clearing primitive native wrapper singleton of small integer";
30553055
Assumption handleValidAssumption = nativeWrapper.getHandleValidAssumption();
30563056
if (hasHandleValidAssumptionProfile.profile(handleValidAssumption != null)) {
3057-
invalidate(handleValidAssumption);
3057+
PythonNativeWrapper.invalidateAssumption(handleValidAssumption);
30583058
}
30593059
}
30603060

@@ -3075,11 +3075,6 @@ static void doOther(@SuppressWarnings("unused") Object delegate, @SuppressWarnin
30753075
// ignore
30763076
}
30773077

3078-
@TruffleBoundary
3079-
private static void invalidate(Assumption assumption) {
3080-
assumption.invalidate("releasing handle for native wrapper");
3081-
}
3082-
30833078
static boolean isPrimitiveNativeWrapper(PythonNativeWrapper nativeWrapper) {
30843079
return nativeWrapper instanceof PrimitiveNativeWrapper;
30853080
}

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/builtins/objects/cext/PythonNativeWrapper.java

Lines changed: 38 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -45,13 +45,15 @@
4545
import com.oracle.graal.python.PythonLanguage;
4646
import com.oracle.truffle.api.Assumption;
4747
import com.oracle.truffle.api.CompilerAsserts;
48+
import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary;
4849
import com.oracle.truffle.api.Truffle;
4950
import com.oracle.truffle.api.dsl.Cached;
5051
import com.oracle.truffle.api.dsl.Cached.Exclusive;
5152
import com.oracle.truffle.api.dsl.Specialization;
5253
import com.oracle.truffle.api.interop.TruffleObject;
5354
import com.oracle.truffle.api.library.ExportLibrary;
5455
import com.oracle.truffle.api.library.ExportMessage;
56+
import com.oracle.truffle.api.nodes.InvalidAssumptionException;
5557

5658
@ExportLibrary(PythonNativeWrapperLibrary.class)
5759
public abstract class PythonNativeWrapper implements TruffleObject {
@@ -98,6 +100,11 @@ public final void setRefCount(long refCount) {
98100
this.refCount = refCount;
99101
}
100102

103+
@TruffleBoundary
104+
public static void invalidateAssumption(Assumption handleValidAssumption) {
105+
handleValidAssumption.invalidate("releasing handle for native wrapper");
106+
}
107+
101108
public final Assumption getHandleValidAssumption() {
102109
return handleValidAssumption;
103110
}
@@ -122,6 +129,15 @@ protected static WeakReference<PythonNativeWrapper> weak(PythonNativeWrapper wra
122129
return new WeakReference<>(wrapper);
123130
}
124131

132+
protected static WeakReference<Assumption> weakAssumption(PythonNativeWrapper wrapper) {
133+
Assumption handleValidAssumption = wrapper.getHandleValidAssumption();
134+
// The assumption only exists if the wrapper was used in a cache at some point.
135+
if (handleValidAssumption != null) {
136+
return new WeakReference<>(handleValidAssumption);
137+
}
138+
return null;
139+
}
140+
125141
@ExportMessage(name = "getDelegate")
126142
protected static class GetDelegate {
127143
@Specialization(guards = {"isEq(cachedWrapper.get(), wrapper)", "!isEq(delegate.get(), null)"}, assumptions = "singleContextAssumption()")
@@ -148,10 +164,16 @@ protected void setDelegate(Object delegate) {
148164

149165
@ExportMessage(name = "getNativePointer")
150166
protected static class GetNativePointer {
151-
@Specialization(guards = {"isEq(cachedWrapper.get(), wrapper)", "!isEq(nativePointer.get(), null)"}, assumptions = "singleContextAssumption()")
167+
@Specialization(guards = {"isEq(cachedWrapper.get(), wrapper)", "!isEq(nativePointer.get(), null)"}, assumptions = "singleContextAssumption()", //
168+
rewriteOn = InvalidAssumptionException.class)
152169
protected static Object getCachedPtr(@SuppressWarnings("unused") PythonNativeWrapper wrapper,
153170
@Exclusive @SuppressWarnings("unused") @Cached("weak(wrapper)") WeakReference<PythonNativeWrapper> cachedWrapper,
154-
@Exclusive @Cached("wrapper.getNativePointerPrivate()") WeakReference<Object> nativePointer) {
171+
@Exclusive @Cached("weakAssumption(wrapper)") WeakReference<Assumption> cachedAssumption,
172+
@Exclusive @Cached("wrapper.getNativePointerPrivate()") WeakReference<Object> nativePointer) throws InvalidAssumptionException {
173+
if (cachedAssumption != null) {
174+
// as long as the wrapper exists, the assumption will also exist
175+
cachedAssumption.get().check();
176+
}
155177
return nativePointer.get();
156178
}
157179

@@ -176,16 +198,27 @@ public void setNativePointer(Object nativePointer) {
176198

177199
@ExportMessage(name = "isNative")
178200
protected static class IsNative {
179-
@Specialization(guards = {"isEq(cachedWrapper.get(), wrapper)", "!isEq(nativePointer.get(), null)"}, assumptions = "singleContextAssumption()")
201+
@Specialization(guards = {"isEq(cachedWrapper.get(), wrapper)", "!isEq(nativePointer.get(), null)"}, assumptions = "singleContextAssumption()", //
202+
rewriteOn = InvalidAssumptionException.class)
180203
protected static boolean isCachedNative(@SuppressWarnings("unused") PythonNativeWrapper wrapper,
181204
@Exclusive @SuppressWarnings("unused") @Cached("weak(wrapper)") WeakReference<PythonNativeWrapper> cachedWrapper,
182-
@Exclusive @SuppressWarnings("unused") @Cached("wrapper.getNativePointerPrivate()") WeakReference<Object> nativePointer) {
205+
@Exclusive @Cached("weakAssumption(wrapper)") WeakReference<Assumption> cachedAssumption,
206+
@Exclusive @SuppressWarnings("unused") @Cached("wrapper.getNativePointerPrivate()") WeakReference<Object> nativePointer) throws InvalidAssumptionException {
207+
if (cachedAssumption != null) {
208+
// as long as the wrapper exists, the assumption will also exist
209+
cachedAssumption.get().check();
210+
}
183211
return true;
184212
}
185213

186214
@Specialization(replaces = "isCachedNative")
187215
protected static boolean isNative(PythonNativeWrapper wrapper) {
188-
return wrapper.nativePointer != null;
216+
if (wrapper.nativePointer != null) {
217+
Assumption handleValidAssumption = wrapper.getHandleValidAssumption();
218+
// If an assumption exists, it must be valid
219+
return handleValidAssumption == null || handleValidAssumption.isValid();
220+
}
221+
return false;
189222
}
190223
}
191224
}

0 commit comments

Comments
 (0)