]> git.notmuchmail.org Git - notmuch/commitdiff
ruby: create an actual wrapper struct
authorFelipe Contreras <felipe.contreras@gmail.com>
Mon, 17 May 2021 19:39:14 +0000 (14:39 -0500)
committerDavid Bremner <david@tethera.net>
Sun, 18 Jul 2021 20:08:42 +0000 (17:08 -0300)
Currently Ruby data points directly to a notmuch object (e.g.
notmuch_database_t), since we don't need any extra data that is fine.

However, in the next commit we will need extra data, therefore we create
a new struct notmuch_rb_object_t wrapper which contains nothing but a
pointer to the current pointer (e.g. notmuch_database_t).

This struct is tied to the Ruby object, and is freed when the Ruby
object is freed by the garbage collector.

We do nothing with this wrapper, so no functionality should be changed.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
bindings/ruby/database.c
bindings/ruby/defs.h
bindings/ruby/init.c

index d6c804ac244bb0693ff78e493fe4699cb7e33462..0159aaac57ca0413132352d6afe42b4bc485cab6 100644 (file)
@@ -81,7 +81,7 @@ notmuch_rb_database_initialize (int argc, VALUE *argv, VALUE self)
        ret = notmuch_database_open (path, mode, &database);
     notmuch_rb_status_raise (ret);
 
-    DATA_PTR (self) = database;
+    DATA_PTR (self) = notmuch_rb_object_create (database);
 
     return self;
 }
index 995bcafd2b0e78e003a9e73419c1805c19e9cd8c..7ddb5df5ae0df3ef02f1cc52a67cf432374dc643 100644 (file)
@@ -66,7 +66,7 @@ extern const rb_data_type_t notmuch_rb_messages_type;
 extern const rb_data_type_t notmuch_rb_message_type;
 extern const rb_data_type_t notmuch_rb_tags_type;
 
-#define Data_Get_Notmuch_Object(obj, type, ptr)                                            \
+#define Data_Get_Notmuch_Rb_Object(obj, type, ptr)                                 \
     do {                                                                           \
        (ptr) = rb_check_typeddata ((obj), (type));                                 \
        if (RB_UNLIKELY (!(ptr))) {                                                 \
@@ -75,8 +75,15 @@ extern const rb_data_type_t notmuch_rb_tags_type;
        }                                                                           \
     } while (0)
 
+#define Data_Get_Notmuch_Object(obj, type, ptr)                        \
+    do {                                                       \
+       notmuch_rb_object_t *rb_wrapper;                        \
+       Data_Get_Notmuch_Rb_Object ((obj), (type), rb_wrapper); \
+       (ptr) = rb_wrapper->nm_object;                          \
+    } while (0)
+
 #define Data_Wrap_Notmuch_Object(klass, type, ptr) \
-    TypedData_Wrap_Struct ((klass), (type), (ptr))
+    TypedData_Wrap_Struct ((klass), (type), notmuch_rb_object_create ((ptr)))
 
 #define Data_Get_Notmuch_Database(obj, ptr) \
     Data_Get_Notmuch_Object ((obj), &notmuch_rb_database_type, (ptr))
@@ -105,16 +112,38 @@ extern const rb_data_type_t notmuch_rb_tags_type;
 #define Data_Get_Notmuch_Tags(obj, ptr) \
     Data_Get_Notmuch_Object ((obj), &notmuch_rb_tags_type, (ptr))
 
+typedef struct {
+    void *nm_object;
+} notmuch_rb_object_t;
+
+static inline void *
+notmuch_rb_object_create (void *nm_object)
+{
+    notmuch_rb_object_t *rb_wrapper = malloc (sizeof (*rb_wrapper));
+    if (RB_UNLIKELY (!rb_wrapper))
+       return NULL;
+
+    rb_wrapper->nm_object = nm_object;
+    return rb_wrapper;
+}
+
+static inline void
+notmuch_rb_object_free (void *rb_wrapper)
+{
+    free (rb_wrapper);
+}
+
 static inline notmuch_status_t
 notmuch_rb_object_destroy (VALUE rb_object, const rb_data_type_t *type)
 {
-    void *nm_object;
+    notmuch_rb_object_t *rb_wrapper;
     notmuch_status_t ret;
 
-    Data_Get_Notmuch_Object (rb_object, type, nm_object);
+    Data_Get_Notmuch_Rb_Object (rb_object, type, rb_wrapper);
 
     /* Call the corresponding notmuch_*_destroy function */
-    ret = ((notmuch_status_t (*)(void *)) type->data) (nm_object);
+    ret = ((notmuch_status_t (*)(void *)) type->data) (rb_wrapper->nm_object);
+    notmuch_rb_object_free (rb_wrapper);
     DATA_PTR (rb_object) = NULL;
 
     return ret;
index d421c6010dc4fddb21c6e081829a0403e1643df1..55c5366e3fc0af8556906ef97b8c1bcd30070ac8 100644 (file)
@@ -48,6 +48,9 @@ ID ID_db_mode;
 
 const rb_data_type_t notmuch_rb_object_type = {
     .wrap_struct_name = "notmuch_object",
+    .function = {
+       .dfree = notmuch_rb_object_free,
+    },
 };
 
 #define define_type(id) \
@@ -55,6 +58,9 @@ const rb_data_type_t notmuch_rb_object_type = {
        .wrap_struct_name = "notmuch_" #id, \
        .parent = &notmuch_rb_object_type, \
        .data = &notmuch_ ## id ## _destroy, \
+       .function = { \
+           .dfree = notmuch_rb_object_free, \
+       }, \
     }
 
 define_type (database);