Неправильный адрес, когда я использую copy_to_user() в загружаемом модуле ядраLinux

Ответить Пред. темаСлед. тема
Anonymous
 Неправильный адрес, когда я использую copy_to_user() в загружаемом модуле ядра

Сообщение Anonymous »

Когда я программировал загружаемый модуль ядра в Linux, я добавил системный вызов, который обходит процессы и сохраняет их в структуре, а затем использует copy_to_user() для копирования структуры из пространства ядра в пространство пользователя. Однако во время процесса copy_to_user() возникла ошибка.
это моя структура:

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

struct process
{
int pid;
int depth;
int have_brother;
char name[16];
}
Ниже приведен код моего модуля.

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

#define free_syscall_num    336             //free syscall number
#define syscall_table_address 0xffffffff8d200320    //syscall table address

long(*save_syscall)(void);                  //Save the original sys_ni_syscall();
unsigned long *syscall_table=0;

struct process a[1000];
int counter = 0;

/*
*Recursively traverse the linux process tree
*/
void preorder_traversal_processtree(struct task_struct *p_task,int b)
{
struct list_head *list;

a[counter].pid = p_task -> pid;
a[counter].depth = b;
if(p_task -> sibling.next == &(p_task->parent->children))
{
a[counter].have_brother=0;
}
else
{
a[counter].have_brother=1;
}

strcpy(a[counter].name,p_task -> comm);
printk("pid: %d\n", a[counter].pid);
counter ++;

list_for_each(list, &p_task->children)
{
printk("pstree is running, counter = %d\n", counter);
struct task_struct *t = list_entry(list, struct task_struct, sibling);
preorder_traversal_processtree(t,b+1);
}

}

/*
The body of the system call
*/
asmlinkage long my_syscall(char __user* buf)
{
counter = 0;
preorder_traversal_processtree(&init_task,0);
if (!access_ok(buf, 1000 * sizeof(struct process)))
{
printk("Invalid user space address\n");
}

if(copy_to_user((struct process *)buf, a, 1000*sizeof(struct process)))
{
printk("Efault\n");
return -EFAULT;

}
else
{
printk("%lu\n",sizeof(a));
return sizeof(a);
}
}

module_init(mymod_init);
module_exit(mymod_exit);
MODULE_LICENSE("GPL");

это мой тестовый код:

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

struct process a[1000];
int brother_reg[100];

int main()
{
int i,j;
int x = syscall(336, &a);

printf("%d\n",a[0].pid);
return 0;
}

Я попробовал протестировать с помощью access_ok() и обнаружил, что адрес недействителен. Когда я тестировал с помощью strace, syscall_0x150() вернул -1 (неверный адрес). Linux — это универсальная версия Linux 5.15.0-105.

Любая помощь будет полезна.

Подробнее здесь: https://stackoverflow.com/questions/784 ... nel-module
Реклама
Ответить Пред. темаСлед. тема

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

  • Похожие темы
    Ответы
    Просмотры
    Последнее сообщение

Вернуться в «Linux»