Skip to content

Commit 1428af3

Browse files
committed
Merge branch 'master' into soft-shutdown
2 parents 66ab719 + 925c166 commit 1428af3

23 files changed

+298
-66
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ This document follows the conventions laid out in [Keep a CHANGELOG][].
1313
- Added function that sets Py_NoSiteFlag to 1.
1414
- Added support for Jetson Nano.
1515
- Added support for __len__ for .NET classes that implement ICollection
16+
- Added `object.GetRawPythonProxy() -> PyObject` extension method, that bypasses any conversions
1617

1718
### Changed
1819

@@ -21,6 +22,7 @@ This document follows the conventions laid out in [Keep a CHANGELOG][].
2122
- Removes PyLong_GetMax and PyClass_New when targetting Python3
2223
- Added support for converting python iterators to C# arrays
2324
- Changed usage of obselete function GetDelegateForFunctionPointer(IntPtr, Type) to GetDelegateForFunctionPointer<TDelegate>(IntPtr)
25+
- When calling C# from Python, enable passing argument of any type to a parameter of C# type `object` by wrapping it into `PyObject` instance. ([#881][i881])
2426
- Added support for kwarg parameters when calling .NET methods from Python
2527

2628
### Fixed

appveyor.yml

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -23,13 +23,10 @@ environment:
2323
BUILD_OPTS: --xplat
2424
- PYTHON_VERSION: 3.7
2525
BUILD_OPTS: --xplat
26-
- PYTHON_VERSION: 3.8
27-
BUILD_OPTS: --xplat
2826
- PYTHON_VERSION: 2.7
2927
- PYTHON_VERSION: 3.5
3028
- PYTHON_VERSION: 3.6
3129
- PYTHON_VERSION: 3.7
32-
- PYTHON_VERSION: 3.8
3330

3431
- PYTHON_VERSION: 3.7
3532
PYTHONNET_SOFT_SHUTDOWN: 1
@@ -39,9 +36,6 @@ matrix:
3936
- PYTHON_VERSION: 3.4
4037
BUILD_OPTS: --xplat
4138
- PYTHON_VERSION: 3.4
42-
- PYTHON_VERSION: 3.8
43-
BUILD_OPTS: --xplat
44-
- PYTHON_VERSION: 3.8
4539

4640
init:
4741
# Update Environment Variables based on matrix/platform

pythonnet.15.sln

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,9 @@ EndProject
1717
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Repo", "Repo", "{441A0123-F4C6-4EE4-9AEE-315FD79BE2D5}"
1818
ProjectSection(SolutionItems) = preProject
1919
.editorconfig = .editorconfig
20+
.gitignore = .gitignore
21+
CHANGELOG.md = CHANGELOG.md
22+
README.rst = README.rst
2023
EndProjectSection
2124
EndProject
2225
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "CI", "CI", "{D301657F-5EAF-4534-B280-B858D651B2E5}"

src/embed_tests/Python.EmbeddingTest.csproj

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,11 +88,13 @@
8888
<Compile Include="pyimport.cs" />
8989
<Compile Include="pyinitialize.cs" />
9090
<Compile Include="pyrunstring.cs" />
91+
<Compile Include="References.cs" />
9192
<Compile Include="TestConverter.cs" />
9293
<Compile Include="TestCustomMarshal.cs" />
9394
<Compile Include="TestDomainReload.cs" />
9495
<Compile Include="TestExample.cs" />
9596
<Compile Include="TestFinalizer.cs" />
97+
<Compile Include="TestInstanceWrapping.cs" />
9698
<Compile Include="TestPyAnsiString.cs" />
9799
<Compile Include="TestPyFloat.cs" />
98100
<Compile Include="TestPyInt.cs" />

src/embed_tests/References.cs

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
namespace Python.EmbeddingTest
2+
{
3+
using NUnit.Framework;
4+
using Python.Runtime;
5+
6+
public class References
7+
{
8+
private Py.GILState _gs;
9+
10+
[SetUp]
11+
public void SetUp()
12+
{
13+
_gs = Py.GIL();
14+
}
15+
16+
[TearDown]
17+
public void Dispose()
18+
{
19+
_gs.Dispose();
20+
}
21+
22+
[Test]
23+
public void MoveToPyObject_SetsNull()
24+
{
25+
var dict = new PyDict();
26+
NewReference reference = Runtime.PyDict_Items(dict.Handle);
27+
try
28+
{
29+
Assert.IsFalse(reference.IsNull());
30+
31+
using (reference.MoveToPyObject())
32+
Assert.IsTrue(reference.IsNull());
33+
}
34+
finally
35+
{
36+
reference.Dispose();
37+
}
38+
}
39+
}
40+
}

src/embed_tests/TestConverter.cs

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
using System;
2+
using System.Collections.Generic;
13
using NUnit.Framework;
24
using Python.Runtime;
35

@@ -44,5 +46,26 @@ public void TestConvertDoubleToManaged(
4446
Assert.IsTrue(converted);
4547
Assert.IsTrue(((double) convertedValue).Equals(testValue));
4648
}
49+
50+
[Test]
51+
public void RawListProxy()
52+
{
53+
var list = new List<string> {"hello", "world"};
54+
var listProxy = list.GetRawPythonProxy();
55+
var clrObject = (CLRObject)ManagedType.GetManagedObject(listProxy.Handle);
56+
Assert.AreSame(list, clrObject.inst);
57+
}
58+
59+
[Test]
60+
public void RawPyObjectProxy()
61+
{
62+
var pyObject = "hello world!".ToPython();
63+
var pyObjectProxy = pyObject.GetRawPythonProxy();
64+
var clrObject = (CLRObject)ManagedType.GetManagedObject(pyObjectProxy.Handle);
65+
Assert.AreSame(pyObject, clrObject.inst);
66+
67+
var proxiedHandle = pyObjectProxy.GetAttr("Handle").As<IntPtr>();
68+
Assert.AreEqual(pyObject.Handle, proxiedHandle);
69+
}
4770
}
4871
}
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
using System;
2+
using System.Globalization;
3+
using NUnit.Framework;
4+
using Python.Runtime;
5+
6+
namespace Python.EmbeddingTest
7+
{
8+
public class TestInstanceWrapping
9+
{
10+
[OneTimeSetUp]
11+
public void SetUp()
12+
{
13+
PythonEngine.Initialize();
14+
}
15+
16+
[OneTimeTearDown]
17+
public void Dispose()
18+
{
19+
PythonEngine.Shutdown();
20+
}
21+
22+
// regression test for https://github.com/pythonnet/pythonnet/issues/811
23+
[Test]
24+
public void OverloadResolution_UnknownToObject()
25+
{
26+
var overloaded = new Overloaded();
27+
using (Py.GIL())
28+
{
29+
var o = overloaded.ToPython();
30+
31+
dynamic callWithSelf = PythonEngine.Eval("lambda o: o.ObjOrClass(object())");
32+
callWithSelf(o);
33+
Assert.AreEqual(Overloaded.Object, overloaded.Value);
34+
}
35+
}
36+
37+
class Base {}
38+
class Derived: Base { }
39+
40+
class Overloaded: Derived
41+
{
42+
public int Value { get; set; }
43+
public void IntOrStr(int arg) => this.Value = arg;
44+
public void IntOrStr(string arg) =>
45+
this.Value = int.Parse(arg, NumberStyles.Integer, CultureInfo.InvariantCulture);
46+
47+
public const int Object = 1;
48+
public const int ConcreteClass = 2;
49+
public void ObjOrClass(object _) => this.Value = Object;
50+
public void ObjOrClass(Overloaded _) => this.Value = ConcreteClass;
51+
52+
public const int Base = ConcreteClass + 1;
53+
public const int Derived = Base + 1;
54+
public void BaseOrDerived(Base _) => this.Value = Base;
55+
public void BaseOrDerived(Derived _) => this.Value = Derived;
56+
}
57+
}
58+
}

src/embed_tests/TestPyScope.cs

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
using System;
2+
using System.Threading;
23
using NUnit.Framework;
34
using Python.Runtime;
45

@@ -340,13 +341,13 @@ public void TestThread()
340341
"import threading\n"+
341342
"lock = threading.Lock()\n"+
342343
"def update():\n" +
343-
" global res, th_cnt\n" +
344-
" with lock:\n" +
345-
" res += bb + 1\n" +
346-
" th_cnt += 1\n"
344+
" global res, th_cnt\n" +
345+
" with lock:\n" +
346+
" res += bb + 1\n" +
347+
" th_cnt += 1\n"
347348
);
348349
}
349-
int th_cnt = 3;
350+
int th_cnt = 100;
350351
for (int i = 0; i < th_cnt; i++)
351352
{
352353
System.Threading.Thread th = new System.Threading.Thread(() =>
@@ -367,7 +368,7 @@ public void TestThread()
367368
{
368369
cnt = ps.Get<int>("th_cnt");
369370
}
370-
System.Threading.Thread.Sleep(10);
371+
Thread.Yield();
371372
}
372373
using (Py.GIL())
373374
{

src/embed_tests/pyimport.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ public void SetUp()
3939

4040
IntPtr str = Runtime.Runtime.PyString_FromString(testPath);
4141
IntPtr path = Runtime.Runtime.PySys_GetObject("path");
42-
Runtime.Runtime.PyList_Append(path, str);
42+
Runtime.Runtime.PyList_Append(new BorrowedReference(path), str);
4343
Runtime.Runtime.XDecref(str);
4444
}
4545

src/runtime/BorrowedReference.cs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,10 @@ readonly ref struct BorrowedReference
1414
public IntPtr DangerousGetAddress()
1515
=> this.IsNull ? throw new NullReferenceException() : this.pointer;
1616

17-
BorrowedReference(IntPtr pointer)
17+
/// <summary>
18+
/// Creates new instance of <see cref="BorrowedReference"/> from raw pointer. Unsafe.
19+
/// </summary>
20+
public BorrowedReference(IntPtr pointer)
1821
{
1922
this.pointer = pointer;
2023
}

0 commit comments

Comments
 (0)