GNU/Linux >> Linux Esercitazione >  >> Linux

Come passare i parametri alla chiamata di sistema Linux?

Devi dire al sistema di compilazione che la tua chiamata di sistema richiede 2 argomenti e che sono di tipo int . Questo è così che gli script che fanno parte del sistema di compilazione genereranno wrapper appropriati per trasmettere gli argomenti nel tipo richiesto. Invece di definire il gestore effettivo come hai fatto tu, dovresti usare -

SYSCALL_DEFINE2(my_syscall_2, int, a, int, b) // Yes, there is a comma between the types and the argument names
{
    printk("my_syscall_2 : %d, %d\n", a, b);
    return b;
}

SYSCALL_DEFINEx è definito in linux/include/linux/syscalls.h.

Puoi guardare un esempio in linux/fs/read_write.c


Ho trovato la soluzione. Come ha risposto @Ajay Brahmakshatriya, dovrei usare la macro SYSCALL_DEFINEx. Inoltre, dovrei modificare arch/x86/entry/syscalls/syscall_64.tbl anche.

Ecco il riepilogo finale.

Come aggiungere nuove chiamate di sistema

Innanzitutto, modifica arch/x86/entry/syscalls/syscall_64.tbl :aggiungi quelle righe sotto.

335     common     my_syscall_0     __x64_sys_my_syscall_0
336     common     my_syscall_1     __x64_sys_my_syscall_1
337     common     my_syscall_2     __x64_sys_my_syscall_2

Secondo, modifica include/linux/syscalls.h :aggiungi quelle righe sotto.

asmlinkage long sys_my_syscall_0(void);
asmlinkage long sys_my_syscall_1(int);
asmlinkage long sys_my_syscall_2(int, int);

Terzo, crea un nuovo file per l'implementazione. Nel mio caso, kernel/my_syscall.c .

#include <linux/syscalls.h>
#include <linux/kernel.h>

SYSCALL_DEFINE0(my_syscall_0)
{
    printk("my_syscall_0\n");
    return 0;
}

SYSCALL_DEFINE1(my_syscall_1, int, a)
{
    printk("my_syscall_1 : %d\n", a);
    return 0;
}

SYSCALL_DEFINE2(my_syscall_2, int, a, int, b)
{
    printk("my_syscall_2 : %d, %d\n", a, b);
    return b;
}

In quarto luogo, aggiungi il file creato a Makefile nella sua directory. Nel mio caso, kernel/Makefile .

...
obj-y = fork.o exec_domain.o panic.o \
        cpu.o exit.o softirq.o resource.o \
        sysctl.o sysctl_binary.o capability.o ptrace.o user.o \
        signal.o sys.o umh.o workqueue.o pid.o task_work.o \
        extable.o params.o \
        kthread.o sys_ni.o nsproxy.o \
        notifier.o ksysfs.o cred.o reboot.o \
        async.o range.o smpboot.o ucount.o \
        my_syscall.o
...

Infine, compila e installa il kernel. Ora sarai in grado di vedere che le nuove chiamate di sistema funzionano bene.

#include <stdio.h>
#include <unistd.h>
#include <sys/syscall.h>

int main()
{
    printf("1 : %d\n", syscall(335));
    printf("2 : %d\n", syscall(336, 1));
    printf("3 : %d\n", syscall(337, 2, 3));
    return 0;
}

dmesg command mi mostra che le chiamate di sistema funzionano bene.

# dmesg
my_syscall_0
my_syscall_1 : 1
my_syscall_2 : 2, 3

Linux
  1. Come configurare la virtualizzazione su Redhat Linux

  2. Come impostare o modificare il nome host del sistema in Linux

  3. Come passare la password al comando SCP in Linux

  4. Come passare i parametri a un alias?

  5. Come eseguire il mmap dello stack per la chiamata di sistema clone() su Linux?

Come passare la password al comando SSH in Linux

Come usare systemctl in Linux

Come usare il comando Linux Strace

Come elencare i servizi su Linux

Come utilizzare il comando fd sul sistema Linux

Come verificare il sistema Linux è a 32 o 64 bit?