Skip to content

Commit 29d7356

Browse files
committed
[GR-65176] Fix errors observed in Macaron.
PullRequest: graalpython/3802
2 parents 786878c + 367270a commit 29d7356

27 files changed

+516
-115
lines changed

graalpython/com.oracle.graal.python.test/src/tests/cpyext/test_ctypes.py

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@
3939
import ctypes
4040
import os.path
4141
import struct
42+
import sys
4243

4344
from tests.cpyext import CPyExtTestCase, CPyExtType
4445

@@ -225,3 +226,27 @@ class MyLargeStruct(ctypes.Structure):
225226
assert result.num7 == 42
226227
finally:
227228
os.chdir(original_cwd)
229+
230+
231+
def test_void_p():
232+
assert ctypes.c_void_p(True).value == ctypes.c_void_p(1).value
233+
assert ctypes.c_void_p(False).value == ctypes.c_void_p(0).value
234+
assert ctypes.c_void_p(2**128 - 1).value == ctypes.c_void_p(2**64 - 1).value
235+
try:
236+
ctypes.c_void_p(2**128 - 1)
237+
except TypeError as e:
238+
assert "cannot be converted to pointer" in str(e)
239+
240+
241+
def test_meson_windows_detect_native_arch() -> str:
242+
if sys.platform != 'win32':
243+
return
244+
process_arch = ctypes.c_ushort()
245+
native_arch = ctypes.c_ushort()
246+
kernel32 = ctypes.windll.kernel32
247+
process = ctypes.c_void_p(kernel32.GetCurrentProcess())
248+
try:
249+
if kernel32.IsWow64Process2(process, ctypes.byref(process_arch), ctypes.byref(native_arch)):
250+
assert native_arch.value == 0x8664, "only amd64 supported by GraalPy on Windows"
251+
except AttributeError as e:
252+
assert "Unknown identifier: IsWow64Process2" in str(e)

graalpython/com.oracle.graal.python.test/src/tests/test_dict.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -172,6 +172,11 @@ def foo(**kwargs):
172172

173173
assert foo(a=5, b=6) == {'a': 1, 'b': 1}
174174

175+
d = dict.fromkeys({'a': 1, 'b': 2, 'c': 3})
176+
assert len(d) == 3
177+
assert set(d.keys()) == {'a', 'b', 'c'}
178+
assert set(d.values()) == {None}
179+
175180

176181
def test_init():
177182
d = dict(a=1, b=2, c=3)

graalpython/com.oracle.graal.python.test/src/tests/test_posix.py

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# Copyright (c) 2018, 2024, Oracle and/or its affiliates. All rights reserved.
1+
# Copyright (c) 2018, 2025, Oracle and/or its affiliates. All rights reserved.
22
# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
33
#
44
# The Universal Permissive License (UPL), Version 1.0
@@ -879,7 +879,6 @@ def test_sysconf_names(self):
879879
self.assertIn('SC_CLK_TCK', os.sysconf_names)
880880

881881
def test_sysconf(self):
882-
self.assertGreaterEqual(os.sysconf('SC_CLK_TCK'), 0)
883882
with self.assertRaisesRegex(TypeError, 'strings or integers'):
884883
os.sysconf(object())
885884
with self.assertRaisesRegex(ValueError, 'unrecognized'):
@@ -892,6 +891,17 @@ def test_sysconf(self):
892891
else:
893892
assert False
894893

894+
# constants taken from POSIX where defined
895+
self.assertGreaterEqual(os.sysconf('SC_ARG_MAX'), 4096)
896+
self.assertGreaterEqual(os.sysconf('SC_CHILD_MAX'), 25)
897+
self.assertGreaterEqual(os.sysconf('SC_LOGIN_NAME_MAX'), 9)
898+
self.assertGreaterEqual(os.sysconf('SC_CLK_TCK'), 0)
899+
self.assertGreaterEqual(os.sysconf('SC_OPEN_MAX'), 20)
900+
self.assertGreaterEqual(os.sysconf('SC_PAGESIZE'), 1)
901+
os.sysconf('SC_SEM_NSEMS_MAX') # returns -1 on my linux box, just check it's there
902+
self.assertGreaterEqual(os.sysconf('SC_PHYS_PAGES'), 1)
903+
self.assertGreaterEqual(os.sysconf('SC_NPROCESSORS_CONF'), 1)
904+
895905

896906
if __name__ == '__main__':
897907
unittest.main()

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/builtins/modules/PosixModuleBuiltins.java

Lines changed: 36 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@
4545
import java.util.ArrayList;
4646
import java.util.Arrays;
4747
import java.util.Collections;
48+
import java.util.LinkedHashMap;
4849
import java.util.List;
4950
import java.util.Map;
5051
import java.util.Map.Entry;
@@ -68,8 +69,6 @@
6869
import com.oracle.graal.python.builtins.objects.buffer.PythonBufferAcquireLibrary;
6970
import com.oracle.graal.python.builtins.objects.bytes.BytesNodes;
7071
import com.oracle.graal.python.builtins.objects.bytes.PBytes;
71-
import com.oracle.graal.python.builtins.objects.common.EconomicMapStorage;
72-
import com.oracle.graal.python.builtins.objects.common.HashingStorageNodes;
7372
import com.oracle.graal.python.builtins.objects.common.SequenceNodes.LenNode;
7473
import com.oracle.graal.python.builtins.objects.common.SequenceStorageNodes;
7574
import com.oracle.graal.python.builtins.objects.common.SequenceStorageNodes.GetItemNode;
@@ -92,6 +91,8 @@
9291
import com.oracle.graal.python.lib.PyNumberIndexNode;
9392
import com.oracle.graal.python.lib.PyOSFSPathNode;
9493
import com.oracle.graal.python.lib.PyObjectAsFileDescriptor;
94+
import com.oracle.graal.python.lib.PyObjectGetAttr;
95+
import com.oracle.graal.python.lib.PyObjectGetItem;
9596
import com.oracle.graal.python.lib.PyObjectSizeNode;
9697
import com.oracle.graal.python.lib.PyUnicodeCheckNode;
9798
import com.oracle.graal.python.nodes.ErrorMessages;
@@ -101,6 +102,7 @@
101102
import com.oracle.graal.python.nodes.call.special.LookupAndCallUnaryNode;
102103
import com.oracle.graal.python.nodes.function.PythonBuiltinBaseNode;
103104
import com.oracle.graal.python.nodes.function.PythonBuiltinNode;
105+
import com.oracle.graal.python.nodes.function.builtins.PythonBinaryBuiltinNode;
104106
import com.oracle.graal.python.nodes.function.builtins.PythonBinaryClinicBuiltinNode;
105107
import com.oracle.graal.python.nodes.function.builtins.PythonClinicBuiltinNode;
106108
import com.oracle.graal.python.nodes.function.builtins.PythonTernaryClinicBuiltinNode;
@@ -252,7 +254,21 @@ public void initialize(Python3Core core) {
252254
PythonLanguage language = core.getLanguage();
253255
addBuiltinConstant("_have_functions", PFactory.createList(language, haveFunctions.toArray()));
254256
addBuiltinConstant("environ", PFactory.createDict(language));
255-
addBuiltinConstant("sysconf_names", PFactory.createDict(language));
257+
258+
LinkedHashMap<String, Object> sysconfigNames = new LinkedHashMap<>();
259+
for (IntConstant name : PosixConstants.sysconfigNames) {
260+
if (name.defined) {
261+
// add the constant without the leading underscore
262+
String pythonName;
263+
if (name.name.startsWith("_")) {
264+
pythonName = name.name.substring(1);
265+
} else {
266+
pythonName = name.name;
267+
}
268+
sysconfigNames.put(pythonName, name.getValueIfDefined());
269+
}
270+
}
271+
addBuiltinConstant("sysconf_names", PFactory.createDictFromMap(language, sysconfigNames));
256272

257273
StructSequence.initType(core, STAT_RESULT_DESC);
258274
StructSequence.initType(core, STATVFS_RESULT_DESC);
@@ -346,9 +362,6 @@ public void postInitialize(Python3Core core) {
346362
Object environAttr = posix.getAttribute(tsLiteral("environ"));
347363
((PDict) environAttr).setDictStorage(environ.getDictStorage());
348364

349-
PDict sysconfNamesAttr = (PDict) posix.getAttribute(tsLiteral("sysconf_names"));
350-
sysconfNamesAttr.setDictStorage(HashingStorageNodes.HashingStorageCopy.executeUncached(SysconfNode.SYSCONF_NAMES));
351-
352365
if (posixLib.getBackend(posixSupport).toJavaStringUncached().equals("java")) {
353366
posix.setAttribute(toTruffleStringUncached("statvfs"), PNone.NO_VALUE);
354367
posix.setAttribute(toTruffleStringUncached("geteuid"), PNone.NO_VALUE);
@@ -2863,50 +2876,43 @@ static int getCpuCount() {
28632876
}
28642877
}
28652878

2866-
@Builtin(name = "sysconf", minNumOfPositionalArgs = 1, parameterNames = {"name"})
2879+
@Builtin(name = "sysconf", minNumOfPositionalArgs = 2, parameterNames = {"$self", "name"}, declaresExplicitSelf = true)
28672880
@GenerateNodeFactory
2868-
abstract static class SysconfNode extends PythonUnaryBuiltinNode {
2881+
abstract static class SysconfNode extends PythonBinaryBuiltinNode {
28692882

2870-
public static final TruffleString T_SC_CLK_TCK = tsLiteral("SC_CLK_TCK");
2871-
public static final TruffleString T_SC_NPROCESSORS_ONLN = tsLiteral("SC_NPROCESSORS_ONLN");
2872-
public static final int SC_CLK_TCK = 2;
2873-
public static final int SC_NPROCESSORS_ONLN = 84;
2874-
public static final EconomicMapStorage SYSCONF_NAMES = EconomicMapStorage.create();
2875-
static {
2876-
// TODO populate from constants
2877-
SYSCONF_NAMES.putUncached(T_SC_CLK_TCK, SC_CLK_TCK);
2878-
SYSCONF_NAMES.putUncached(T_SC_NPROCESSORS_ONLN, SC_NPROCESSORS_ONLN);
2879-
}
2883+
private static final TruffleString T_SYSCONF_NAMES = tsLiteral("sysconf_names");
28802884

28812885
@Specialization
2882-
static int sysconf(VirtualFrame frame, Object arg,
2886+
static long sysconf(VirtualFrame frame, PythonModule self, Object arg,
28832887
@Bind("this") Node inliningTarget,
28842888
@Cached PyLongCheckNode longCheckNode,
28852889
@Cached PyLongAsIntNode asIntNode,
28862890
@Cached PyUnicodeCheckNode unicodeCheckNode,
2887-
@Cached HashingStorageNodes.HashingStorageGetItem getItem,
2891+
@Cached PyObjectGetAttr getAttr,
2892+
@Cached PyObjectGetItem getItem,
28882893
@Cached PRaiseNode raiseNode,
2894+
@Bind PythonContext context,
2895+
@CachedLibrary("context.getPosixSupport()") PosixSupportLibrary posixLib,
28892896
@Cached PConstructAndRaiseNode.Lazy constructAndRaiseNode) {
28902897
int id;
28912898
if (longCheckNode.execute(inliningTarget, arg)) {
28922899
id = asIntNode.execute(frame, inliningTarget, arg);
28932900
} else if (unicodeCheckNode.execute(inliningTarget, arg)) {
2894-
Object idObj = getItem.execute(frame, inliningTarget, SYSCONF_NAMES, arg);
2895-
if (idObj instanceof Integer idInt) {
2896-
id = idInt;
2897-
} else {
2901+
try {
2902+
Object sysconfigNamesObject = getAttr.execute(frame, inliningTarget, self, T_SYSCONF_NAMES);
2903+
Object idObj = getItem.execute(frame, inliningTarget, sysconfigNamesObject, arg);
2904+
id = asIntNode.execute(frame, inliningTarget, idObj);
2905+
} catch (PException e) {
28982906
throw raiseNode.raise(inliningTarget, ValueError, ErrorMessages.UNRECOGNIZED_CONF_NAME);
28992907
}
29002908
} else {
29012909
throw raiseNode.raise(inliningTarget, TypeError, ErrorMessages.CONFIGURATION_NAMES_MUST_BE_STRINGS_OR_INTEGERS);
29022910
}
2903-
if (id == SC_CLK_TCK) {
2904-
return 100; // it's 100 on most default kernel configs. TODO: use real value through
2905-
// NFI
2906-
} else if (id == SC_NPROCESSORS_ONLN) {
2907-
return CpuCountNode.getCpuCount();
2911+
try {
2912+
return posixLib.sysconf(context.getPosixSupport(), id);
2913+
} catch (PosixException e) {
2914+
throw constructAndRaiseNode.get(inliningTarget).raiseOSErrorFromPosixException(frame, e);
29082915
}
2909-
throw constructAndRaiseNode.get(inliningTarget).raiseOSError(frame, OSErrorEnum.EINVAL);
29102916
}
29112917
}
29122918

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/builtins/modules/ctypes/CFieldBuiltins.java

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -725,19 +725,14 @@ static Object Z_set(@SuppressWarnings("unused") FieldSet setfunc, Pointer ptr, O
725725
@Specialization(guards = "setfunc == P_set")
726726
static Object P_set(@SuppressWarnings("unused") FieldSet setfunc, Pointer ptr, Object value, @SuppressWarnings("unused") int size,
727727
@Bind("this") Node inliningTarget,
728-
@Exclusive @Cached PyLongCheckNode longCheckNode,
729728
@Exclusive @Cached PointerNodes.PointerFromLongNode pointerFromLongNode,
730-
@Exclusive @Cached PointerNodes.WritePointerNode writePointerNode,
731-
@Exclusive @Cached PRaiseNode raiseNode) {
729+
@Exclusive @Cached PointerNodes.WritePointerNode writePointerNode) {
732730
Pointer valuePtr;
733731
if (value == PNone.NONE) {
734732
valuePtr = Pointer.NULL;
735-
} else if (longCheckNode.execute(inliningTarget, value)) {
736-
valuePtr = pointerFromLongNode.execute(inliningTarget, value);
737733
} else {
738-
throw raiseNode.raise(inliningTarget, TypeError, ErrorMessages.CANNOT_BE_CONVERTED_TO_POINTER);
734+
valuePtr = pointerFromLongNode.execute(inliningTarget, value);
739735
}
740-
741736
writePointerNode.execute(inliningTarget, ptr, valuePtr);
742737
return PNone.NONE;
743738
}

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/builtins/modules/ctypes/memory/PointerNodes.java

Lines changed: 35 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -41,9 +41,12 @@
4141
package com.oracle.graal.python.builtins.modules.ctypes.memory;
4242

4343
import static com.oracle.graal.python.builtins.PythonBuiltinClassType.NotImplementedError;
44+
import static com.oracle.graal.python.builtins.PythonBuiltinClassType.OverflowError;
4445
import static com.oracle.graal.python.builtins.modules.ctypes.CtypesNodes.WCHAR_T_SIZE;
4546
import static com.oracle.graal.python.util.PythonUtils.ARRAY_ACCESSOR;
4647

48+
import java.math.BigInteger;
49+
4750
import com.oracle.graal.python.builtins.modules.ctypes.memory.Pointer.ByteArrayStorage;
4851
import com.oracle.graal.python.builtins.modules.ctypes.memory.Pointer.LongPointerStorage;
4952
import com.oracle.graal.python.builtins.modules.ctypes.memory.Pointer.MemoryBlock;
@@ -58,14 +61,15 @@
5861
import com.oracle.graal.python.builtins.objects.cext.PythonNativeVoidPtr;
5962
import com.oracle.graal.python.builtins.objects.cext.capi.CExtNodes;
6063
import com.oracle.graal.python.builtins.objects.cext.capi.transitions.CApiTransitions;
64+
import com.oracle.graal.python.builtins.objects.ints.PInt;
6165
import com.oracle.graal.python.builtins.objects.memoryview.PMemoryView;
6266
import com.oracle.graal.python.nodes.ErrorMessages;
6367
import com.oracle.graal.python.nodes.PRaiseNode;
64-
import com.oracle.graal.python.nodes.util.CastToJavaUnsignedLongNode;
6568
import com.oracle.graal.python.runtime.PythonContext;
6669
import com.oracle.graal.python.util.PythonUtils;
6770
import com.oracle.truffle.api.CompilerDirectives;
6871
import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary;
72+
import com.oracle.truffle.api.HostCompilerDirectives.InliningCutoff;
6973
import com.oracle.truffle.api.dsl.Cached;
7074
import com.oracle.truffle.api.dsl.Fallback;
7175
import com.oracle.truffle.api.dsl.GenerateCached;
@@ -790,11 +794,36 @@ static Pointer doNativeVoidPtr(PythonNativeVoidPtr value) {
790794
return Pointer.nativeMemory(pointerObject);
791795
}
792796

793-
@Fallback
794-
static Pointer doLong(Node inliningTarget, Object value,
795-
@Cached CastToJavaUnsignedLongNode cast) {
796-
long pointer = cast.execute(inliningTarget, value);
797-
return Pointer.nativeMemory(pointer);
797+
@Specialization
798+
static Pointer doBool(Node inliningTarget, boolean value) {
799+
return Pointer.nativeMemory(value ? 1 : 0);
800+
}
801+
802+
@Specialization
803+
static Pointer doLong(Node inliningTarget, long value) {
804+
return Pointer.nativeMemory(value);
805+
}
806+
807+
@Specialization
808+
static Pointer doPInt(Node inliningTarget, PInt value) {
809+
return Pointer.nativeMemory(value.longValue());
810+
}
811+
812+
@Specialization
813+
@TruffleBoundary
814+
@InliningCutoff
815+
static Pointer doGeneric(Node inliningTarget, Object value,
816+
@CachedLibrary(limit = "1") InteropLibrary lib) {
817+
if (lib.fitsInBigInteger(value)) {
818+
BigInteger bi;
819+
try {
820+
bi = lib.asBigInteger(value);
821+
return doLong(inliningTarget, bi.longValue());
822+
} catch (UnsupportedMessageException e) {
823+
// fall through to error
824+
}
825+
}
826+
throw PRaiseNode.raiseStatic(inliningTarget, OverflowError, ErrorMessages.CANNOT_BE_CONVERTED_TO_POINTER);
798827
}
799828
}
800829

graalpython/com.oracle.graal.python/src/com/oracle/graal/python/builtins/modules/pickle/PUnpickler.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -769,7 +769,7 @@ protected HashingStorage getClonedHashingStorage(VirtualFrame frame, Object obj)
769769
CompilerDirectives.transferToInterpreterAndInvalidate();
770770
getHashingStorageNode = insert(HashingCollectionNodes.GetClonedHashingStorageNode.create());
771771
}
772-
return getHashingStorageNode.doNoValueCached(frame, obj);
772+
return getHashingStorageNode.getForSetsCached(frame, obj);
773773
}
774774

775775
private void setItem(VirtualFrame frame, Object object, Object key, Object value) {

0 commit comments

Comments
 (0)