Выделение памяти под GList (Разница между g_list_alloc() и g_malloc(sizeof(GList)))

Модератор: Модераторы разделов

ttnl
Сообщения: 18
ОС: Debian Etch

Выделение памяти под GList

Сообщение ttnl »

Помогите понять, в чем разница между выделением памяти с помощью
g_list_alloc() и с помощью g_malloc(sizeof(GList)).


Дело в том, что в моей программе при использовании:
1)g_list_alloc для выделения памяти под новую ссылку и
2)g_list_free1 для освобождения ссылки
все работает хорошо.

Если использовать
1)g_malloc и
2)g_list_free1
при той же последовательности действий, что и в первом случае,
то возникает ошибка:
glibc: corrupted double-linked list
и программа падает.

А если использовать
1)g_malloc() и
2)g_free(),
то все опять работает хорошо

Т.е. g_list_alloc делает что-то побочное, помимо выделения памяти?
(Зачем он сделан через g_slice, а не через g_malloc?)
Спасибо сказали:
d_n_k
Сообщения: 636
ОС: Gentoo GNU/Linux

Re: Выделение памяти под GList

Сообщение d_n_k »

g_list_alloc инициализарует список, а g_malloc всего лишь выделяет память.поэтому и ошибка, тк список не инициализированный

g_list_free1 - уничтожает спиксок, те функция уничтожет весь списко, а не только память под первый элемент

g_free - тупо забирает память обратно, без каких-либо проверок того указателя который ей передали

почитай что есть список и как он выглядит в памяти, тогда поймешь разницу
все сказанное есть имхо...
Спасибо сказали:
ttnl
Сообщения: 18
ОС: Debian Etch

Re: Выделение памяти под GList

Сообщение ttnl »

Все-таки g_list_free_1 () освобождает один элемент списка.

"Frees one GList element. It is usually used after g_list_remove_link()"

А вот структура GList:
struct _GList
{
gpointer data;
GList *next;
GList *prev;
};


Не понимаю, что она может инициализировать. Все три указателя я явным образом
устанавливаю в нуль после malloc'а.

Если можно, объясните, пожалуйста, немного более научно-популярно.
Спасибо сказали:
d_n_k
Сообщения: 636
ОС: Gentoo GNU/Linux

Re: Выделение памяти под GList

Сообщение d_n_k »

начно-популярно: смотри исходники glib :)

Код: Выделить всё

#define  g_slice_new0(type)     ((type*) g_slice_alloc0 (sizeof (type)))
#define _g_list_alloc0()        g_slice_new0 (GList)

GList*
g_list_alloc (void)
{
  return _g_list_alloc0 ();
}


gpointer
g_slice_alloc0 (gsize mem_size)
{
  gpointer mem = g_slice_alloc (mem_size);
  if (mem)
    memset (mem, 0, mem_size);
  return mem;
}


#define _g_list_free1(list)     g_slice_free (GList, list)

#define g_slice_free(type, mem)                do {    \
  if (1) g_slice_free1 (sizeof (type), (mem));            \
  else   (void) ((type*) 0 == (mem));                 \
} while (0)

void
g_list_free_1 (GList *list)
{
  _g_list_free1 (list);
}


void
g_slice_free1 (gsize    mem_size,
               gpointer mem_block)
{
...// много букф
}


что делает g_malloc и g_free смотри сам
все сказанное есть имхо...
Спасибо сказали:
pktfag
Сообщения: 142
ОС: Arch Linux

Re: Выделение памяти под GList

Сообщение pktfag »

А зачем что-то выделять? В документации сказано:
There is no function to create a GList. NULL is considered to be the empty list so you simply set a GList* to NULL.

Просто делаешь:

Код: Выделить всё

GList *plugins=NULL;

А потом:

Код: Выделить всё

plugins=g_list_append(plugins,(gpointer)filename);

В g_list_append, как я понимаю, вся память, что нужна, выделится.
Освобождать так:

Код: Выделить всё

g_list_free(plugins);

Или, если для каждого filename нужно очистить память, то:

Код: Выделить всё

GList *ptr;
for(ptr=plugins;ptr;ptr=ptr->next) g_free(ptr->data);
g_list_free(plugins);
Спасибо сказали: