@@ -16,54 +16,40 @@ internal class MethodBinding : ExtensionType
16
16
{
17
17
internal MaybeMethodInfo info ;
18
18
internal MethodObject m ;
19
- internal IntPtr target ;
20
- internal IntPtr targetType ;
19
+ internal PyObject ? target ;
20
+ internal PyType targetType ;
21
21
22
- public MethodBinding ( MethodObject m , IntPtr target , IntPtr targetType )
22
+ public MethodBinding ( MethodObject m , PyObject ? target , PyType ? targetType = null )
23
23
{
24
- Runtime . XIncref ( target ) ;
25
24
this . target = target ;
26
25
27
- if ( targetType == IntPtr . Zero )
28
- {
29
- targetType = Runtime . PyObject_Type ( target ) ;
30
- }
31
- else
32
- {
33
- Runtime . XIncref ( targetType ) ;
34
- }
35
-
36
- this . targetType = targetType ;
26
+ this . targetType = targetType ?? target . GetPythonType ( ) ;
37
27
38
28
this . info = null ;
39
29
this . m = m ;
40
30
}
41
31
42
- public MethodBinding ( MethodObject m , IntPtr target ) : this ( m , target , IntPtr . Zero )
43
- {
44
- }
45
-
46
32
/// <summary>
47
33
/// Implement binding of generic methods using the subscript syntax [].
48
34
/// </summary>
49
- public static IntPtr mp_subscript ( IntPtr tp , IntPtr idx )
35
+ public static NewReference mp_subscript ( BorrowedReference tp , BorrowedReference idx )
50
36
{
51
- var self = ( MethodBinding ) GetManagedObject ( tp ) ;
37
+ var self = ( MethodBinding ) GetManagedObject ( tp ) ! ;
52
38
53
- Type [ ] types = Runtime . PythonArgsToTypeArray ( idx ) ;
39
+ Type [ ] ? types = Runtime . PythonArgsToTypeArray ( idx ) ;
54
40
if ( types == null )
55
41
{
56
42
return Exceptions . RaiseTypeError ( "type(s) expected" ) ;
57
43
}
58
44
59
- MethodInfo mi = MethodBinder . MatchParameters ( self . m . info , types ) ;
45
+ MethodInfo ? mi = MethodBinder . MatchParameters ( self . m . info , types ) ;
60
46
if ( mi == null )
61
47
{
62
48
return Exceptions . RaiseTypeError ( "No match found for given type params" ) ;
63
49
}
64
50
65
51
var mb = new MethodBinding ( self . m , self . target ) { info = mi } ;
66
- return mb . pyHandle ;
52
+ return new NewReference ( mb . pyHandle ) ;
67
53
}
68
54
69
55
PyObject Signature
@@ -131,37 +117,35 @@ public int Compare(Type a, Type b)
131
117
/// <summary>
132
118
/// MethodBinding __getattribute__ implementation.
133
119
/// </summary>
134
- public static IntPtr tp_getattro ( IntPtr ob , IntPtr key )
120
+ public static NewReference tp_getattro ( BorrowedReference ob , BorrowedReference key )
135
121
{
136
- var self = ( MethodBinding ) GetManagedObject ( ob ) ;
122
+ var self = ( MethodBinding ) GetManagedObject ( ob ) ! ;
137
123
138
124
if ( ! Runtime . PyString_Check ( key ) )
139
125
{
140
126
Exceptions . SetError ( Exceptions . TypeError , "string expected" ) ;
141
- return IntPtr . Zero ;
127
+ return default ;
142
128
}
143
129
144
- string name = InternString . GetManagedString ( key ) ;
130
+ string ? name = InternString . GetManagedString ( key ) ;
145
131
switch ( name )
146
132
{
147
133
case "__doc__" :
148
- IntPtr doc = self . m . GetDocString ( ) ;
149
- Runtime . XIncref ( doc ) ;
150
- return doc ;
134
+ return self . m . GetDocString ( ) ;
151
135
// FIXME: deprecate __overloads__ soon...
152
136
case "__overloads__" :
153
137
case "Overloads" :
154
138
var om = new OverloadMapper ( self . m , self . target ) ;
155
- return om . pyHandle ;
139
+ return new NewReference ( om . pyHandle ) ;
156
140
case "__signature__" when Runtime . InspectModule is not null :
157
141
var sig = self . Signature ;
158
142
if ( sig is null )
159
143
{
160
144
return Runtime . PyObject_GenericGetAttr ( ob , key ) ;
161
145
}
162
- return sig . NewReferenceOrNull ( ) . DangerousMoveToPointerOrNull ( ) ;
146
+ return sig . NewReferenceOrNull ( ) ;
163
147
case "__name__" :
164
- return self . m . GetName ( ) . DangerousMoveToPointerOrNull ( ) ;
148
+ return self . m . GetName ( ) ;
165
149
default :
166
150
return Runtime . PyObject_GenericGetAttr ( ob , key ) ;
167
151
}
@@ -171,9 +155,9 @@ public static IntPtr tp_getattro(IntPtr ob, IntPtr key)
171
155
/// <summary>
172
156
/// MethodBinding __call__ implementation.
173
157
/// </summary>
174
- public static IntPtr tp_call ( IntPtr ob , IntPtr args , IntPtr kw )
158
+ public static NewReference tp_call ( BorrowedReference ob , BorrowedReference args , BorrowedReference kw )
175
159
{
176
- var self = ( MethodBinding ) GetManagedObject ( ob ) ;
160
+ var self = ( MethodBinding ) GetManagedObject ( ob ) ! ;
177
161
178
162
// This works around a situation where the wrong generic method is picked,
179
163
// for example this method in the tests: string Overloaded<T>(int arg1, int arg2, string arg3)
@@ -183,11 +167,11 @@ public static IntPtr tp_call(IntPtr ob, IntPtr args, IntPtr kw)
183
167
if ( info . IsGenericMethod )
184
168
{
185
169
var len = Runtime . PyTuple_Size ( args ) ; //FIXME: Never used
186
- Type [ ] sigTp = Runtime . PythonArgsToTypeArray ( args , true ) ;
170
+ Type [ ] ? sigTp = Runtime . PythonArgsToTypeArray ( args , true ) ;
187
171
if ( sigTp != null )
188
172
{
189
173
Type [ ] genericTp = info . GetGenericArguments ( ) ;
190
- MethodInfo betterMatch = MethodBinder . MatchSignatureAndParameters ( self . m . info , genericTp , sigTp ) ;
174
+ MethodInfo ? betterMatch = MethodBinder . MatchSignatureAndParameters ( self . m . info , genericTp , sigTp ) ;
191
175
if ( betterMatch != null )
192
176
{
193
177
self . info = betterMatch ;
@@ -200,32 +184,32 @@ public static IntPtr tp_call(IntPtr ob, IntPtr args, IntPtr kw)
200
184
// as the first argument. Note that this is not supported if any
201
185
// of the overloads are static since we can't know if the intent
202
186
// was to call the static method or the unbound instance method.
203
- var disposeList = new List < IntPtr > ( ) ;
187
+ var disposeList = new List < PyObject > ( ) ;
204
188
try
205
189
{
206
- IntPtr target = self . target ;
190
+ PyObject ? target = self . target ;
207
191
208
- if ( target == IntPtr . Zero && ! self . m . IsStatic ( ) )
192
+ if ( target is null && ! self . m . IsStatic ( ) )
209
193
{
210
194
var len = Runtime . PyTuple_Size ( args ) ;
211
195
if ( len < 1 )
212
196
{
213
197
Exceptions . SetError ( Exceptions . TypeError , "not enough arguments" ) ;
214
- return IntPtr . Zero ;
198
+ return default ;
215
199
}
216
- target = Runtime . PyTuple_GetItem ( args , 0 ) ;
217
- Runtime . XIncref ( target ) ;
200
+ target = new PyObject ( Runtime . PyTuple_GetItem ( args , 0 ) ) ;
218
201
disposeList . Add ( target ) ;
219
202
220
- args = Runtime . PyTuple_GetSlice ( args , 1 , len ) ;
221
- disposeList . Add ( args ) ;
203
+ var unboundArgs = Runtime . PyTuple_GetSlice ( args , 1 , len ) . MoveToPyObject ( ) ;
204
+ disposeList . Add ( unboundArgs ) ;
205
+ args = unboundArgs ;
222
206
}
223
207
224
208
// if the class is a IPythonDerivedClass and target is not the same as self.targetType
225
209
// (eg if calling the base class method) then call the original base class method instead
226
210
// of the target method.
227
211
IntPtr superType = IntPtr . Zero ;
228
- if ( Runtime . PyObject_TYPE ( target ) != self . targetType )
212
+ if ( target is not null && Runtime . PyObject_TYPE ( target ) != self . targetType )
229
213
{
230
214
var inst = GetManagedObject ( target ) as CLRObject ;
231
215
if ( inst ? . inst is IPythonDerivedType )
@@ -234,15 +218,14 @@ public static IntPtr tp_call(IntPtr ob, IntPtr args, IntPtr kw)
234
218
if ( baseType != null && baseType . type . Valid )
235
219
{
236
220
string baseMethodName = "_" + baseType . type . Value . Name + "__" + self . m . name ;
237
- IntPtr baseMethod = Runtime . PyObject_GetAttrString ( target , baseMethodName ) ;
238
- if ( baseMethod != IntPtr . Zero )
221
+ using var baseMethod = Runtime . PyObject_GetAttrString ( target , baseMethodName ) ;
222
+ if ( ! baseMethod . IsNull ( ) )
239
223
{
240
- var baseSelf = GetManagedObject ( baseMethod ) as MethodBinding ;
224
+ var baseSelf = GetManagedObject ( baseMethod . Borrow ( ) ) as MethodBinding ;
241
225
if ( baseSelf != null )
242
226
{
243
227
self = baseSelf ;
244
228
}
245
- Runtime . XDecref ( baseMethod ) ;
246
229
}
247
230
else
248
231
{
@@ -251,13 +234,13 @@ public static IntPtr tp_call(IntPtr ob, IntPtr args, IntPtr kw)
251
234
}
252
235
}
253
236
}
254
- return self . m . Invoke ( target , args , kw , self . info . UnsafeValue ) ;
237
+ return self . m . Invoke ( target is null ? BorrowedReference . Null : target , args , kw , self . info . UnsafeValue ) ;
255
238
}
256
239
finally
257
240
{
258
- foreach ( IntPtr ptr in disposeList )
241
+ foreach ( var ptr in disposeList )
259
242
{
260
- Runtime . XDecref ( ptr ) ;
243
+ ptr . Dispose ( ) ;
261
244
}
262
245
}
263
246
}
@@ -266,12 +249,12 @@ public static IntPtr tp_call(IntPtr ob, IntPtr args, IntPtr kw)
266
249
/// <summary>
267
250
/// MethodBinding __hash__ implementation.
268
251
/// </summary>
269
- public static nint tp_hash ( IntPtr ob )
252
+ public static nint tp_hash ( BorrowedReference ob )
270
253
{
271
- var self = ( MethodBinding ) GetManagedObject ( ob ) ;
254
+ var self = ( MethodBinding ) GetManagedObject ( ob ) ! ;
272
255
nint x = 0 ;
273
256
274
- if ( self . target != IntPtr . Zero )
257
+ if ( self . target is not null )
275
258
{
276
259
x = Runtime . PyObject_Hash ( self . target ) ;
277
260
if ( x == - 1 )
@@ -292,18 +275,18 @@ public static nint tp_hash(IntPtr ob)
292
275
/// <summary>
293
276
/// MethodBinding __repr__ implementation.
294
277
/// </summary>
295
- public static IntPtr tp_repr ( IntPtr ob )
278
+ public static NewReference tp_repr ( BorrowedReference ob )
296
279
{
297
- var self = ( MethodBinding ) GetManagedObject ( ob ) ;
298
- string type = self . target == IntPtr . Zero ? "unbound" : "bound" ;
280
+ var self = ( MethodBinding ) GetManagedObject ( ob ) ! ;
281
+ string type = self . target is null ? "unbound" : "bound" ;
299
282
string name = self . m . name ;
300
283
return Runtime . PyString_FromString ( $ "<{ type } method '{ name } '>") ;
301
284
}
302
285
303
286
protected override void Clear ( )
304
287
{
305
- Runtime . Py_CLEAR ( ref this . target ) ;
306
- Runtime . Py_CLEAR ( ref this . targetType ) ;
288
+ this . target = null ;
289
+ this . targetType = null ! ;
307
290
base . Clear ( ) ;
308
291
}
309
292
0 commit comments