2014-03-12 9 views
10

Als ich durch den unteren Chunk von Linux Char-Treiber-Code ging, fand ich den Strukturzeiger current in printk."Current" in Linux-Kernel-Code

Ich möchte wissen, welche Struktur der current zeigt und seine vollständigen Elemente.

Welchen Zweck erfüllt diese Struktur?

+2

Es sieht aus wie es eine Struktur ist, die auf den Prozess bezieht, die den Systemaufruf gemacht. – Barmar

+1

Probieren Sie googling für 'Annotated Linux Kernel', Sie sollten einige hilfreiche Ressourcen finden. – Barmar

+4

http://kernelnewbies.org/FAQ/current – cnicutar

Antwort

18

Es ist ein Zeiger auf den aktuellen Prozess, dh der Prozess, der den Systemaufruf ausgelöst hat.

Vom docs:

Der aktuelle Prozess

Obwohl Kernel-Module nicht ausgeführt werden sequentiell als Anwendungen tun, meisten Aktionen vom Kernel ausgeführt werden, zu einem bestimmten Prozess. Kernel-Code kann den aktuellen Prozess durch Zugriff auf die globale Element aktuelle, ein Zeiger auf Struktur struct task_struct, , die ab Version 2.4 des Kernels in <asm/current.h>, enthalten durch <linux/sched.h>. Der aktuelle Zeiger verweist auf den aktuell ausgeführten Benutzerprozess. Während der Ausführung eines Systemaufrufs , wie Öffnen oder Lesen, ist der aktuelle Prozess derjenige , der den Aufruf aufgerufen hat. Kernel-Code kann prozessspezifische Informationen mithilfe von Strom verwenden, wenn es erforderlich ist. Ein Beispiel für diese Technik ist in "Zugriffskontrolle auf eine Gerätedatei" in Kapitel 5, "Erweiterte Char-Treiber-Operationen" dargestellt.

Eigentlich ist Strom nicht richtig eine globale Variable, wie es in den ersten Linux-Kernel war. Die Entwickler optimierten den Zugriff auf die -Struktur, die den aktuellen Prozess beschreibt, indem sie ihn auf der Stack-Seite verbergen. Sie können die Details der aktuellen in betrachten. Während der Code, den Sie betrachten, haarig scheint, müssen wir daran denken, dass Linux ein SMP-kompatibles System ist und eine globale Variable einfach nicht funktioniert, wenn Sie mit mehreren CPUs beschäftigen. Die Details der Implementierung bleiben jedoch für andere Kernel-Subsysteme verborgen, und ein Gerätetreiber kann einfach den aktuellen Prozess einschließen und darauf verweisen.

Aus der Sicht eines Moduls ist Strom genau wie die externe Referenz printk. Ein Modul kann sich dort, wo es passt, auf Strom beziehen. Zum Beispiel druckt die folgende Anweisung den Prozess-ID und die Befehlsnamen des aktuellen Prozesses durch bestimmte Felder in struct task_struct Zugriff:

printk("The process is \"%s\" (pid %i)\n", 
    current->comm, current->pid); 

Der Befehlsname in strom- gespeichert> comm ist der Basisname von die Programmdatei, die vom aktuellen Prozess ausgeführt wird.

4

Dies ist die komplette Struktur der „aktuellen“ zeigt auf

task_struct 
Each task_struct data structure describes a process or task in the system. 

struct task_struct { 
/* these are hardcoded - don't touch */ 
    volatile long  state;   /* -1 unrunnable, 0 runnable, >0 stopped */ 
    long     counter; 
    long     priority; 
    unsigned    long signal; 
    unsigned    long blocked; /* bitmap of masked signals */ 
    unsigned    long flags;  /* per process flags, defined below */ 
    int errno; 
    long     debugreg[8]; /* Hardware debugging registers */ 
    struct exec_domain *exec_domain; 
/* various fields */ 
    struct linux_binfmt *binfmt; 
    struct task_struct *next_task, *prev_task; 
    struct task_struct *next_run, *prev_run; 
    unsigned long  saved_kernel_stack; 
    unsigned long  kernel_stack_page; 
    int     exit_code, exit_signal; 
    /* ??? */ 
    unsigned long  personality; 
    int     dumpable:1; 
    int     did_exec:1; 
    int     pid; 
    int     pgrp; 
    int     tty_old_pgrp; 
    int     session; 
    /* boolean value for session group leader */ 
    int     leader; 
    int     groups[NGROUPS]; 
    /* 
    * pointers to (original) parent process, youngest child, younger sibling, 
    * older sibling, respectively. (p->father can be replaced with 
    * p->p_pptr->pid) 
    */ 
    struct task_struct *p_opptr, *p_pptr, *p_cptr, 
         *p_ysptr, *p_osptr; 
    struct wait_queue *wait_chldexit; 
    unsigned short  uid,euid,suid,fsuid; 
    unsigned short  gid,egid,sgid,fsgid; 
    unsigned long  timeout, policy, rt_priority; 
    unsigned long  it_real_value, it_prof_value, it_virt_value; 
    unsigned long  it_real_incr, it_prof_incr, it_virt_incr; 
    struct timer_list real_timer; 
    long     utime, stime, cutime, cstime, start_time; 
/* mm fault and swap info: this can arguably be seen as either 
    mm-specific or thread-specific */ 
    unsigned long  min_flt, maj_flt, nswap, cmin_flt, cmaj_flt, cnswap; 
    int swappable:1; 
    unsigned long  swap_address; 
    unsigned long  old_maj_flt; /* old value of maj_flt */ 
    unsigned long  dec_flt;  /* page fault count of the last time */ 
    unsigned long  swap_cnt;  /* number of pages to swap on next pass */ 
/* limits */ 
    struct rlimit  rlim[RLIM_NLIMITS]; 
    unsigned short  used_math; 
    char     comm[16]; 
/* file system info */ 
    int     link_count; 
    struct tty_struct *tty;   /* NULL if no tty */ 
/* ipc stuff */ 
    struct sem_undo  *semundo; 
    struct sem_queue  *semsleeping; 
/* ldt for this task - used by Wine. If NULL, default_ldt is used */ 
    struct desc_struct *ldt; 
/* tss for this task */ 
    struct thread_struct tss; 
/* filesystem information */ 
    struct fs_struct  *fs; 
/* open file information */ 
    struct files_struct *files; 
/* memory management info */ 
    struct mm_struct  *mm; 
/* signal handlers */ 
    struct signal_struct *sig; 
#ifdef __SMP__ 
    int     processor; 
    int     last_processor; 
    int     lock_depth;  /* Lock depth. 
              We can context switch in and out 
              of holding a syscall kernel lock... */ 
#endif 
}; 
+0

Aus der obigen Frage: 'Welchen Zweck dient diese Struktur?' – dragosht