pycall 1.5.3 → 1.5.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: cbe8667d161e27770570029b6e2da005db45d5f2e61482ba7ffa96117fa82a61
4
- data.tar.gz: 530c510c0accfc3b1af1daf69ad530855ecf943ffaf6dd9d47975bf7f89132a7
3
+ metadata.gz: 4c46a9c4f077cebbd72eb6cbbd73ed78dbc25157758b18dd0875f6a454a9a25b
4
+ data.tar.gz: 82b308675e78c3b9bfeb84d7019ec7fee85b3ed1b0cb748b88dcffb94be4152c
5
5
  SHA512:
6
- metadata.gz: 179af9a8a76e9f4528990468e8eb776c9031390cea2f28219c3da8aaf5dbc017df1cf2dfdf254b549a9313800ec640f82d4ca5302d6b74d3b192cc79daaf896b
7
- data.tar.gz: 71a248181b886b513a650aef95a583563d5bb34e125e8f0bc1dc838e47c8ab6d38480bfe77d017065c73c47177dccab6d5a27b28d666b401e325fb118e95ea30
6
+ metadata.gz: 311f23b5ca9052a100231138d1879df2ef19464e071a75176120141f9b4d3bd6b5e2b6d8fa35f356593e07cbd74366ef4be9c87cac85928dce652b9e60021e2b
7
+ data.tar.gz: 8135204a29e333294c768b8d407b8e9cd546e92dce497ea811a9ee2aa91cbfa63b1b5c04f14f555447ab2b6a138b13a40520ea8c80529606f0532a0f8c5a3ad6
data/CHANGES.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # The change history of PyCall
2
2
 
3
+ ## 1.5.4
4
+
5
+ * Fix GC compaction related crash (#230, #231).
6
+
7
+ *himotoyoshi*
8
+
3
9
  ## 1.5.3
4
10
 
5
11
  * Add support for Ruby 4.1 (#225).
data/ext/pycall/pycall.c CHANGED
@@ -10,27 +10,58 @@ VALUE mLibPython;
10
10
  VALUE mAPI;
11
11
  VALUE mHelpers;
12
12
  VALUE mConversion;
13
- VALUE mPyObjectWrapper;
14
- VALUE mPyTypeObjectWrapper;
15
13
  VALUE mGCGuard;
16
14
 
17
15
  VALUE pycall_cPyPtr;
18
16
  VALUE cPyTypePtr;
19
- VALUE cTuple;
20
- VALUE cPyError;
21
17
 
22
- VALUE pycall_eError;
23
-
24
- static VALUE pycall_libpython_handle;
25
18
  static VALUE python_description;
26
19
  static VALUE python_version_string;
27
20
  static Py_ssize_t python_hexversion;
28
21
  static int python_major_version;
29
22
  static int python_has_stackless_extension;
30
23
  static PyObject *python_builtins_module;
31
- static VALUE python_type_mapping;
32
24
  static ID id_python_type_mapping;
33
25
 
26
+ /* Don't keep Ruby objects that aren't pinned in C global variables.
27
+ * They may be moved by GC compaction. */
28
+
29
+ static inline VALUE
30
+ libpython_handle(void)
31
+ {
32
+ return rb_funcall(mLibPython, rb_intern("handle"), 0);
33
+ }
34
+
35
+ static inline VALUE
36
+ pyobject_wrapper_module(void)
37
+ {
38
+ return rb_const_get_at(mPyCall, rb_intern("PyObjectWrapper"));
39
+ }
40
+
41
+ static inline VALUE
42
+ pytypeobject_wrapper_module(void)
43
+ {
44
+ return rb_const_get_at(mPyCall, rb_intern("PyTypeObjectWrapper"));
45
+ }
46
+
47
+ static inline VALUE
48
+ error_class(void)
49
+ {
50
+ return rb_const_get_at(mPyCall, rb_intern("Error"));
51
+ }
52
+
53
+ static inline VALUE
54
+ pyerror_class(void)
55
+ {
56
+ return rb_const_get_at(mPyCall, rb_intern("PyError"));
57
+ }
58
+
59
+ static inline VALUE
60
+ python_type_mapping(void)
61
+ {
62
+ return rb_ivar_get(mConversion, id_python_type_mapping);
63
+ }
64
+
34
65
  int
35
66
  pycall_python_major_version(void)
36
67
  {
@@ -1470,7 +1501,7 @@ pycall_libpython_helpers_m_sequence_each(VALUE mod, VALUE pyptr)
1470
1501
  static int
1471
1502
  is_pyobject_wrapper(VALUE obj)
1472
1503
  {
1473
- return RTEST(rb_obj_is_kind_of(obj, mPyObjectWrapper));
1504
+ return RTEST(rb_obj_is_kind_of(obj, pyobject_wrapper_module()));
1474
1505
  }
1475
1506
 
1476
1507
  static VALUE
@@ -1523,7 +1554,7 @@ pycall_python_type_mapping_get_mapped_ancestor_class(VALUE pytypeptr)
1523
1554
  args[0] = pytypeptr;
1524
1555
  args[1] = Qnil;
1525
1556
 
1526
- rb_hash_foreach(python_type_mapping, get_mapped_ancestor_class_iter, (VALUE)args);
1557
+ rb_hash_foreach(python_type_mapping(), get_mapped_ancestor_class_iter, (VALUE)args);
1527
1558
 
1528
1559
  return args[1];
1529
1560
  }
@@ -1533,7 +1564,7 @@ pycall_python_type_mapping_get_mapped_class(VALUE pytypeptr)
1533
1564
  {
1534
1565
  VALUE mapped;
1535
1566
  (void)check_get_pytypeobj_ptr(pytypeptr);
1536
- mapped = rb_hash_lookup(python_type_mapping, pytypeptr);
1567
+ mapped = rb_hash_lookup(python_type_mapping(), pytypeptr);
1537
1568
  if (NIL_P(mapped)) {
1538
1569
  mapped = pycall_python_type_mapping_get_mapped_ancestor_class(pytypeptr);
1539
1570
  }
@@ -1544,16 +1575,16 @@ static int
1544
1575
  pycall_python_type_mapping_register(VALUE pytypeptr, VALUE rbcls)
1545
1576
  {
1546
1577
  (void)check_get_pytypeobj_ptr(pytypeptr);
1547
- if (rb_hash_lookup2(python_type_mapping, pytypeptr, Qundef) != Qundef)
1578
+ if (rb_hash_lookup2(python_type_mapping(), pytypeptr, Qundef) != Qundef)
1548
1579
  return 0;
1549
1580
 
1550
1581
  Check_Type(rbcls, T_CLASS);
1551
- if (!rb_obj_is_kind_of(rbcls, mPyTypeObjectWrapper)) {
1582
+ if (!rb_obj_is_kind_of(rbcls, pytypeobject_wrapper_module())) {
1552
1583
  rb_raise(rb_eTypeError, "ruby class must be extended by PyCall::PyTypeObjectWrapper");
1553
1584
  }
1554
1585
 
1555
1586
  /* TODO: Shouldn't have to use weak reference? */
1556
- rb_hash_aset(python_type_mapping, pytypeptr, rbcls);
1587
+ rb_hash_aset(python_type_mapping(), pytypeptr, rbcls);
1557
1588
 
1558
1589
  return 1;
1559
1590
  }
@@ -1562,10 +1593,10 @@ static int
1562
1593
  pycall_python_type_mapping_unregister(VALUE pytypeptr)
1563
1594
  {
1564
1595
  (void)check_get_pytypeobj_ptr(pytypeptr);
1565
- if (rb_hash_lookup2(python_type_mapping, pytypeptr, Qundef) == Qundef)
1596
+ if (rb_hash_lookup2(python_type_mapping(), pytypeptr, Qundef) == Qundef)
1566
1597
  return 0;
1567
1598
 
1568
- rb_hash_delete(python_type_mapping, pytypeptr);
1599
+ rb_hash_delete(python_type_mapping(), pytypeptr);
1569
1600
  return 1;
1570
1601
  }
1571
1602
 
@@ -1576,7 +1607,7 @@ pycall_pyobject_wrapper_object_new(VALUE klass, PyObject *pyobj)
1576
1607
 
1577
1608
  obj = rb_obj_alloc(klass);
1578
1609
  rb_ivar_set(obj, rb_intern("@__pyptr__"), pycall_pyptr_new(pyobj));
1579
- rb_extend_object(obj, mPyObjectWrapper);
1610
+ rb_extend_object(obj, pyobject_wrapper_module());
1580
1611
 
1581
1612
  return obj;
1582
1613
  }
@@ -2166,7 +2197,7 @@ pycall_pyerror_new(PyObject *type, PyObject *value, PyObject *traceback)
2166
2197
  init_args[1] = value ? pycall_pyobject_to_ruby(value) : Qnil;
2167
2198
  init_args[2] = traceback ? pycall_pyobject_to_ruby(traceback) : Qnil;
2168
2199
 
2169
- return rb_class_new_instance(3, init_args, cPyError);
2200
+ return rb_class_new_instance(3, init_args, pyerror_class());
2170
2201
  }
2171
2202
 
2172
2203
  VALUE
@@ -2200,7 +2231,7 @@ pycall_pyerror_fetch_and_raise(char const *format, ...)
2200
2231
  msg = rb_vsprintf(format, args);
2201
2232
  va_end(args);
2202
2233
 
2203
- rb_exc_raise(rb_exc_new3(eError, msg));
2234
+ rb_exc_raise(rb_exc_new3(error_class(), msg));
2204
2235
  }
2205
2236
 
2206
2237
  unsigned long
@@ -2331,7 +2362,7 @@ init_python(void)
2331
2362
  Py_API(Py_IncRef)((PyObject *)Py_API(PyUnicode_Type));
2332
2363
  rb_define_const(mAPI, "PyUnicode_Type", pycall_pytypeptr_new((PyObject *)Py_API(PyUnicode_Type)));
2333
2364
 
2334
- pycall_init_exceptions(pycall_libpython_handle);
2365
+ pycall_init_exceptions(libpython_handle());
2335
2366
  }
2336
2367
 
2337
2368
  static VALUE
@@ -2392,6 +2423,7 @@ pycall_pyerror_s_fetch(VALUE klass)
2392
2423
  static void
2393
2424
  init_pyerror(void)
2394
2425
  {
2426
+ VALUE cPyError = pyerror_class();
2395
2427
  rb_define_singleton_method(cPyError, "occurred?", pycall_pyerror_s_occurred_p, 0);
2396
2428
  rb_define_singleton_method(cPyError, "fetch", pycall_pyerror_s_fetch, 0);
2397
2429
  }
@@ -2399,7 +2431,7 @@ init_pyerror(void)
2399
2431
  static void
2400
2432
  init_tuple(void)
2401
2433
  {
2402
- cTuple = rb_funcall(mPyCall, rb_intern("wrap_class"), 1, pycall_pytypeptr_new((PyObject *)Py_API(PyTuple_Type)));
2434
+ VALUE cTuple = rb_funcall(mPyCall, rb_intern("wrap_class"), 1, pycall_pytypeptr_new((PyObject *)Py_API(PyTuple_Type)));
2403
2435
  rb_define_const(mPyCall, "Tuple", cTuple);
2404
2436
  rb_funcall(cTuple, rb_intern("register_python_type_mapping"), 0);
2405
2437
  rb_define_singleton_method(cTuple, "new", pycall_tuple_s_new, -1);
@@ -2414,11 +2446,7 @@ Init_pycall(void)
2414
2446
  pycall_hash_salt = FIX2LONG(rb_hash(rb_str_new2("PyCall::PyObject")));
2415
2447
 
2416
2448
  mPyCall = rb_define_module("PyCall");
2417
- mPyObjectWrapper = rb_const_get_at(mPyCall, rb_intern("PyObjectWrapper"));
2418
- mPyTypeObjectWrapper = rb_const_get_at(mPyCall, rb_intern("PyTypeObjectWrapper"));
2419
2449
  mGCGuard = rb_define_module_under(mPyCall, "GCGuard");
2420
- eError = rb_const_get_at(mPyCall, rb_intern("Error"));
2421
- cPyError = rb_const_get_at(mPyCall, rb_intern("PyError"));
2422
2450
 
2423
2451
  /* PyCall */
2424
2452
 
@@ -2470,8 +2498,7 @@ Init_pycall(void)
2470
2498
  /* PyCall::LibPython::API */
2471
2499
 
2472
2500
  mLibPython = rb_define_module_under(mPyCall, "LibPython");
2473
- pycall_libpython_handle = rb_funcall(mLibPython, rb_intern("handle"), 0);
2474
- pycall_init_libpython_api_table(pycall_libpython_handle);
2501
+ pycall_init_libpython_api_table(libpython_handle());
2475
2502
 
2476
2503
  mAPI = rb_define_module_under(mLibPython, "API");
2477
2504
 
@@ -2513,9 +2540,8 @@ Init_pycall(void)
2513
2540
  rb_define_module_function(mConversion, "from_ruby", pycall_conv_m_from_ruby, 1);
2514
2541
  rb_define_module_function(mConversion, "to_ruby", pycall_conv_m_to_ruby, 1);
2515
2542
 
2516
- python_type_mapping = rb_hash_new();
2517
2543
  id_python_type_mapping = rb_intern("__python_type_mapping__");
2518
- rb_ivar_set(mConversion, id_python_type_mapping, python_type_mapping);
2544
+ rb_ivar_set(mConversion, id_python_type_mapping, rb_hash_new());
2519
2545
 
2520
2546
  /* initialize the constat PYTHON_VERSION */
2521
2547
 
@@ -746,11 +746,9 @@ void pycall_init_ruby_wrapper(void);
746
746
  extern intptr_t pycall_hash_salt;
747
747
  extern VALUE pycall_mPyCall;
748
748
  extern VALUE pycall_cPyPtr;
749
- extern VALUE pycall_eError;
750
749
 
751
750
  #define mPyCall pycall_mPyCall
752
751
  #define cPyPtr pycall_cPyPtr
753
- #define eError pycall_eError
754
752
 
755
753
  /* #define PYCALL_DEBUG_DUMP_REFCNT */
756
754
 
@@ -1,5 +1,5 @@
1
1
  module PyCall
2
- VERSION = "1.5.3"
2
+ VERSION = "1.5.4"
3
3
 
4
4
  module Version
5
5
  numbers, TAG = VERSION.split("-")
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pycall
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.5.3
4
+ version: 1.5.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Kenta Murata
@@ -217,7 +217,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
217
217
  - !ruby/object:Gem::Version
218
218
  version: '0'
219
219
  requirements: []
220
- rubygems_version: 4.0.16
220
+ rubygems_version: 4.0.20
221
221
  specification_version: 4
222
222
  summary: pycall
223
223
  test_files: []