(inout) (transfer full) annotations for container types
- From: Sergio Mariotti <sergio mariotti it gmail com>
- To: gir-devel-list gnome org
- Subject: (inout) (transfer full) annotations for container types
- Date: Sat, 7 Feb 2015 22:43:22 +0100
Hello,
I have a question regarding (inout) (transfer full) annotations applied to container types (e.g. GArray, GHashTable types).
Consider if we have an annotation such as:
@array: (inout) (element-type utf8) (transfer full):
where array is of type GArray. It seems to me that there are multiple ways of dealing with how to free the array:
a) if the array has a clear function set (via g_array_set_clear_function()) then a single call to g_array_unref() will free both the array and member elements.
b) if the array does not have a clear function set then each element must be freed + a call to g_array_unref() to free the array in order to avoid memory leaks.
Unfortunately the (inout) + (transfer full) annotation leaves me confused as to which of the above two options should be followed. Thus I have the following question:
* does the (transfer full) annotation applied to an array type mean that it's both safe and required to free array member elements before freeing the array itsef? i.e. if a clear function is set must there instead be a (transfer container) annotation?
I noticed that the gimarshallingtests.c file from the gobject-introspection source code contains a number of (inout) (transfer full) examples, some of which would require option a) from above, while others would require option b) from above:
example 1.
* GArray 'result' will not automatically free member elements when the array is destroyed.
/**
* gi_marshalling_tests_garray_utf8_full_inout:
* @array_: (inout) (element-type utf8) (transfer full):
*/
void
gi_marshalling_tests_garray_utf8_full_inout (GArray **array_)
{
static gchar *val1 = "-1";
static gchar *val2 = "-2";
gchar *val;
GArray *result;
g_assert_cmpint ((*array_)->len, ==, 3);
g_assert_cmpstr (g_array_index (*array_, gchar *, 0), ==, "0");
g_assert_cmpstr (g_array_index (*array_, gchar *, 1), ==, "1");
g_assert_cmpstr (g_array_index (*array_, gchar *, 2), ==, "2");
result = g_array_new (TRUE, TRUE, sizeof (gchar *));
val = g_strdup (val2);
g_array_append_val (result, val);
val = g_strdup (val1);
g_array_append_val (result, val);
val = g_strdup ("0");
g_array_append_val (result, val);
val = g_strdup ("1");
g_array_append_val (result, val);
g_array_unref (*array_);
*array_ = result;
}
example 2. (inout) (transfer full)
* GHashTable 'result' contains functions that will automatically free keys&values when the hash table is destroyed
/**
* gi_marshalling_tests_ghashtable_utf8_full_inout:
* @hash_table: (inout) (element-type utf8 utf8) (transfer full):
*/
void
gi_marshalling_tests_ghashtable_utf8_full_inout (GHashTable **hash_table)
{
GHashTable *result = g_hash_table_new_full (g_str_hash, g_str_equal,
g_free, g_free);
g_assert_cmpstr (g_hash_table_lookup (*hash_table, "-1"), ==, "1");
g_assert_cmpstr (g_hash_table_lookup (*hash_table, "0"), ==, "0");
g_assert_cmpstr (g_hash_table_lookup (*hash_table, "1"), ==, "-1");
g_assert_cmpstr (g_hash_table_lookup (*hash_table, "2"), ==, "-2");
g_hash_table_insert (result, g_strdup ("-1"), g_strdup ("1"));
g_hash_table_insert (result, g_strdup ("0"), g_strdup ("0"));
g_hash_table_insert (result, g_strdup ("1"), g_strdup ("1"));
g_hash_table_unref (*hash_table);
*hash_table = result;
}
Regards
Sergio
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]