"Linux kernel Design and implementation" Chapter III study notes

Source: Internet
Author: User

Chapter III Process Management

Name: Wang Wei No.: 20135116

First, the process

1, the meaning of the process

A process is a program of execution and a generic term for related resources, and the program itself is not a process, it is actually a real-time result of the code being executed. The Linux kernel often calls processes also " tasks ".

2, the meaning of the thread

The thread of execution threads is the object that interacts in the process. the kernel Dispatches objects that are threads rather than processes. Linux systems do not differentiate between threads and processes, and threads are just a special process.

3, the process of the implementation process

(1) Clone () calls fork () to create a completely new process by copying an existing process, and the process begins to survive. The process in which the fork () is called is the parent process , and the newly generated process is a child process . At the end of the system call, at the same location as the return point, the parent process replies to execution and the child process begins execution. Where thefork () system call returns two times from the kernel : one time back to the parent process and another to the newly generated child process. The difference between a child process and a parent process is the PID (unique per process), PPID (the process number of the parent process, which the child process sets as the PID of the copied process), and some resources and statistics.

(2) The new process calls the Exec () function, creates a new address space, and loads the new program into it.

(3) The program launches execution through the exit () system call, ends the process and frees the resource it occupies, and the process exits after execution in a zombie state until the parent process calls wait () or waitpid () . Where the parent process can query whether the child process is terminated through the WAIT4 () system call.

Ii. process descriptors and task structures

  The kernel stores the list of processes in the "task queue" in a two-way circular chain table. Each item in the list is a structure of type task_struct, called the process descriptor , which is defined in the <linux/sched.h> file, and the process descriptor contains all the information for a specific process.

1. Assigning process descriptors

Linux distributes the TASK_STRUCT structure dynamically through the slab allocator, which achieves object reuse and cache coloring (cache coloring). Simply create a new struct struct thread_info at the bottom of the stack (the stack that is growing down) or the top of the stack (the stack that grows upward).

The THREAD_INFO structure of each task is allocated at the end of its kernel stack. A task field in a structure field holds a pointer to the actual task_struct of the task.

2. Process Descriptor Storage

The kernel identifies each process through a unique process identity value or PID. The PID is a number, expressed as a pid_t implicit type, which is actually an int type with a maximum default set of 32768 (the maximum value for short int). The maximum default value indicates the maximum number of simultaneous processes allowed in the system, and the smaller the value, the faster it is to turn around.

Accessing a task in the kernel usually requires a pointer to its task_struct. In fact, most of the code in the kernel's processing process is done directly through task_struct.

3. Process status

The State field in the process descriptor describes the current status of the process.

(1) Five states of the process

    • TASK RUNNING (Run): The process is executable, indicating that it is executing or waiting to be executed in the run queue.
    • Task_interruptible (interruptible): The process is hibernating (blocked), waiting for a certain condition to be reached.
    • Task_uninterruptible (non-interruptible): In addition to receiving a signal that is not awakened or ready to run, this state, like the interruptible state, usually occurs when the process must wait without interference or when the wait time is soon to occur.
    • __task_reaced: A process that is tracked by another process, for example, by ptrace the debugger.
    • __task_stopped: The process is stalled and the process is not operational or operational

(2) Process State transformation

4. Set Current process status

Use the Set_task_state (task,state) function to set the established process to the established state.

* Note: set_current_state (state) and set_task_state (task,state) mean the same.

5. Process context

When a program call executes a system call or triggers an exception, it falls into kernel space, where we say the kernel "executes on behalf of the process" and is in the context of the process. The current macro is valid in this context.

Processes can only be stuck in kernel execution through some well-defined interfaces-all access to the kernel must pass through these interfaces.

6. Process Family Tree

All processes are descendants of the init process with PID 1. The relationship between processes is stored in the process descriptor, and each task_struct contains a pointer to its parent process task_struct, called parent, and a list of child processes called children.

Third, process creation

1. Copy when writing

(1) Linux fork () uses the write-time copy (Copy-on-write) page implementation, the kernel does not replicate the entire process address space, but rather let the parent process and the child process share a copy, and fork () the actual cost is to copy the parent process's page table and create a unique process descriptor for the child process.

(2) The replication of a resource only occurs when a write is required, before which it is shared only in read-only mode.

(3) Under normal circumstances, the process is created immediately after the execution of an executable file, this optimization can avoid copying large amounts of redundant data.

2. Fork ()

(1) the fork (), vfork (), and __clone () library functions invoke clone () according to their required parameter flags, and then call Do_fork () by Clone ().

(2) the Do_fork () function calls the Copy_process () function, and if the copy_process () function returns successfully, the newly created child process is awakened and put into operation, and the kernel intentionally chooses the child process to execute first.

(3) about the Copy_process () function:

    • call Dup_task_struct () create a kernel stack, thread_info structure, and task_ for the new process struct, these values are consistent with the current value
    • Check to make sure that the child process is newly created. The number of processes owned by the current user does not exceed the limit of the resources allocated to it.
    • copy_process () calls Copy_flags () to update task_ The flags member of the struct.
    • call Alloc_pid () assigns a valid PID to the new process.
    • Copy or share open files, copy_process () according to the parameter flags passed to clone () File system information, signal processing functions, process address space, namespaces, and so on.

3, Vfork ()

(1) The vfork () system call and the fork () function are the same except for page table entries that do not copy the parent process. The child process runs as a separate thread of the parent process in its address space, and the parent process is blocked until the child process launches or executes EXEC ().

(2) Ideally, the system is best not to call Vfork (), the kernel does not have to implement it.

(3) The implementation of the Vfork () system call is done by passing a special flag to the Clone () system call.

    • When Copy_process () is called, the Vfor_done member of TASK_STRUCT is set to null.
    • When Do_fork () is executed, if a special flag is given, vfork_done points to a specific address .
    • After the child process begins execution, the parent process does not resume execution immediately , but waits until the child process sends a signal to it through the Vfork_done pointer.
    • When mm_release () is called, the function is used for the process to exit the memory address space and to check if Vfork_done is empty, and if not NULL, a signal is sent to the parent process.
    • Back to Do_fork (), the parent process wakes up and returns.

Iv. implementation of threads in Linux

Each thread has a unique task_struct of its own, so in the kernel it looks like a normal process.

1. Creating Threads

Creating a thread is similar to creating a normal process, except that you need to pass some parameter flags when invoking clone () to indicate which resources need to be shared:

The parameter flags passed to clone () determine how the new creation process behaves and what kind of resources are common among the parent-child processes.

2. Kernel thread

(1) The difference between kernel threads and ordinary process widths is that kernel threads do not have separate address spaces (actually, the MM pointers to the address space are set to null), they run only in kernel space and never switch to user space.

(2) kernel processes, like normal processes, can be scheduled or preempted.

(3) Kernel Chan Cheng can only be created chimneys other kernels Chan Cheng

    • The new task is created by the Kthread kernel process through the clone () system call.
    • The newly created process is in a non-operational state, and it does not actively run if it is not explicitly awakened by calling Wake_up _process ().
    • Create a process and let it run, you can call Ktbread_run ().
    • After the kernel Chan Cheng is started, it runs until the call Do_exit () exits, or the other part of the kernel calls Kthread_stop () exits.

V. The end of the process

In general, process destruction is caused by itself. It occurs when the process calls the exit () system call, which either explicitly calls this system call or implicitly returns from the main function of a program (the C language compiler places the code for forlorn with exit () after the return point of the main () function.

The end of the process relies mostly on do_exit ():

  • Set the flag member in Tast_struct to Pf_exiting.
  • Call Del_timer_ Sync () to remove any kernel timers. Based on the returned results, it ensures that no timers are queued and that a timer handler is running.
  • If the BSD process accounting function is turned on, Do_exit () calls Acct_update_ integrals () to output the accounting information.
  • Then call the EXIT_MM () function to release the mm_struct that the process occupies, and if no other process uses them, completely release them.
  • Next Call the Sem_ exit () function. If the process waits for an IPC signal, it leaves the queue.
  • Call Exit_files () and Exit_fs () to separate the reference count for the file descriptor, file system data, respectively.
  • The task exit code stored in the Exit_code member of the task_struct is then set to the exit code provided by exit (), or to any other exit action specified by the kernel mechanism.
  • Call Exit_notify () to send a signal to the parent process, re-find the adoptive father (other threads in the thread group or the INIT process), and set the process state (stored in the exit_state of the task_struct structure) to exit_zomble.
  • Do_exit () calls schedule () to switch to the new process.

At this point, all resources associated with the process are freed, the thread is not operational (and there is no address space to run it) and is in the Exit_zombie exit state.

1. Delete Process Descriptor

Wait () This family function is implemented through a unique (but very complex) system call to WAIT4 (). Its standard action is to suspend the process that invokes it until one of the child processes exits, and the function returns the PID of the child process.

When the process descriptor needs to be released eventually, Release_task () is called to do the following:

2. The dilemma caused by the orphan process

If the parent process exits before the child process, there must be a mechanism to ensure that the child process can find a new parent, otherwise these orphaned processes will always be in a zombie state at the time of the exit, in vain for the memory to be wasted.

* Workaround:

For the child process to find a thread within the current thread group as the father, if not, let Init do their parent process. Exit_notify () is called in Do_exit (), which calls Forget_original_parent () and the latter invokes Find_new _reaper () to perform the parent-seeking process.

When a process is tracked, its temporary father is set to debug the process . a way to find a new parent process: search for the associated sibling process in a single ptrace-tracked sub-process list one by one with two relatively small links to reduce the cost of traversal.

This chapter summarizes:

    • How Linux stores and represents processes (with task_ struct and thread_info)
    • How to create a process (via fork (), in effect, eventually clone ())
    • How to load a new execution image into an address space (through the EXECO system call family)
    • How to represent the hierarchical relationship of a process, and how the parent process collects information about its descendants (through the wait () system call family)
    • How the process eventually dies (forced or voluntary call to exit ())

"Linux kernel Design and implementation" Chapter III study notes

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.