Я удаляю каждый элемент из списка ядра и копируя его содержимое в пользовательский буфер (удаляя каждый элемент, если он подходит). Я делаю это synchrone, поэтому я включил семафоры, как я делаю процесс удаления, удалив из списка в режиме синхронизации и вставив его в другой список, затем я разблокирую код и удалю из нового списка. Количество элементов копируется в строки Окс прав, но при выполнении (находится недалеко от конца):Удаление элементов из списка ядра
printk(KERN_INFO "item->data: %d",item->data);
результат когда-либо: item-> Данные: 111
Это не должно случиться потому что item-> data является случайным числом, поэтому удаление приводит к сбою памяти, но я не знаю, как его исправить или даже проблема.
list_item_t структура такова:
typedef struct {
int data;
struct list_head links;
}list_item_t;
Мой список декларации:
struct list_head mylist = LIST_HEAD_INIT(mylist);
Вот код, который создает проблемы.
static ssize_t modtimer_read (struct file *file, char *user, size_t nbits, loff_t * offset){
struct list_head* pos = mylist.next; // The position of the list
struct list_head* auxpos;
struct list_head listaux = LIST_HEAD_INIT(listaux);
list_item_t* item;
char aux[MAX_BUFFER];
char aux2[10];
int total =0;
int subt =0;
int done = 0;
printk(KERN_INFO "modtimer_read open");
if (down_interruptible(&mtx)) /*Lock*/
return -EINTR;
while (done == 0){
if(pos == pos->next || list_num_items == 0){
done++;
printk(KERN_INFO "Empty list");
// Esperar
}else{
item = list_entry(pos, list_item_t, links); //gets the item in the 'pos' position
subt=sprintf(aux2, "%d\n",item->data);
auxpos = pos->next;
if(subt + total > MAX_BUFFER) {
done++;
printk(KERN_INFO "string has maximum size");
}else {
total+= sprintf(&aux[total],"%i\n",item->data); //reads the data (integer)
list_add_tail(&listaux,pos); //Added into the aux list
list_del(pos); //deleted from the list
list_num_items--;
}
subt = 0;
pos = auxpos;
}
}
aux[total] = '\0';
up(&mtx);
pos = listaux.next;
while(&listaux != listaux.next){
item = list_entry(pos, list_item_t, links); //gets the item in the 'pos' position
auxpos = pos->next;
list_del(pos);
printk(KERN_INFO "item->data: %d",item->data);
vfree(item);
pos = auxpos;
}
copy_to_user(user,aux,total);
printk(KERN_INFO "modtimer_read cerrado");
return total;
}
Итак, что вы думаете? Я добавляю в список помощников, чтобы удалить позже. Док просто говорит: «Вставьте новую запись перед указанной головой. Это полезно для реализации очередей». – Kaostias