操做系統中的進程和線程

操做系統中的進程和線程

1.進程和線程的學習中容易混亂的地方

之因此以爲進程和線程難以理解,大概有這麼幾個緣由:html

  • 進程,線程的概念是不斷髮展的,不一樣時期的書籍會有不一樣的闡述,如一開始內核不支持線程到後來內核開始支持線程
  • 經典的書籍如《現代操做系統》可能是從原理的角度去說,高屋建瓴,可是難以有切身感覺
  • 操做系統對進程和線程的實現也是不一樣的,架構者對進程和線程的理念有所不一樣,Linux和Windows內核對線程的實現不一樣。

2.進程模型的演變

最初,進程的內涵分爲兩個方面:linux

  • 調度,執行的基本單位

最初操做系統不支持線程的概念,內核中維護着進程的各類信息,如運行狀態,優先級,寄存器等,也就是說OS能夠根據這些信息調度和執行進程。算法

  • 資源全部權

包括程序,數據,文件,socket 等資源。編程

將兩個獨立的功能分離,出現了線程的概念:windows

  • 做爲執行與調度的基本單位——thread
  • 資源全部權: process

這也就是常常說的:"process是資源容器,thread是執行單位"。這樣帶來的巨大好處是:多線程

  • 線程的建立成本遠遠低於進程,由於線程中包含的數據量少於進程,線程只須要執行相關的數據便可,如,pc,寄存器,棧,執行狀態
  • 進程中的線程共享地址空間,進程間的通訊的代價遠大於線程間的通訊。

3.三種線程模型

<1>用戶級線程

彼時操做系統沒有提供對線程的支持,只是在應用層面實現了線程,操做系統並不知道,,內核維護着進程表,仍然以進程爲單位進行系統調用。進程自身維護着線程表,維護線程的狀態。架構

  • 優點socket

    • 不用切換到內核態,性能極佳,
    • 進程本身能夠有定製的調度算法
    • 在不支持多線程的操做系統實現多線程程序,如DOS
  • 劣勢性能

    • 對線程的操做,如建立,調度,都是應用程序實現,致使編程困難
    • 由於操做系統只知進程不知線程,也就只能調度進程而沒法調度線程,全部只要一個線程所在的進程發生了阻塞,那操做系統即阻塞該進程,那麼該進程的其餘線程也就沒法被調度,至關於阻塞了。目前使用用戶線程的程序愈來愈少了。
<2>內核級線程

後來,操做系統內核開始支持線程,就出現了內核級線程模型。這種線程模型中,內核維護着進程表和線程表,也就是說,內核能夠對線程直接進行調度,學習

  • 優點

    • 內核的調度粒度小至線程,就不會出現用戶級進程那種阻塞了進程,進程中全部線程都被迫「阻塞」的狀況,內核線程被阻塞,不會致使進程被阻塞,進程中的其餘線程依然能夠繼續執行
  • 劣勢

    • 開銷挺大,從用戶態到內核態的切換有必定的開銷
    • 支持的線程總量較小,由於內核線程佔據內核的空間,而內核所持有的空間是有限的

通常而言,程序不會直接使用內核線程,而是使用內核線程的高級接口——輕量級進程。輕量級進程和內核線程是1:1的關係。

<3>混合線程

有些操做系統支持,如Solaris平臺。比較主流的windows和linux不支持。

4.歸納進程和線程的本質

  • 進程:當用戶啓動一個應用,系統將程序的源碼和數據從磁盤加載到內存中,而且開始執行他的源碼。一個進程即一個正被執行中的程序。與程序不一樣, 一個進程是一個活躍的實體 ,而且包含了程序做爲單個實例在執行期間狀態的快照。
  • 線程:一個線程的本質是一組寄存器的狀態,是操做系統對寄存器狀態的抽象

5.特殊的Linux線程實現

Linux對進程與線程的實現比較特殊,對於Linux內核來講,並不存在線程的說法,可是Linux中進程與進程能夠是有區別的。對於linux內核來講,只有進程,建立進使用系統調用clone,可經過設置該方法的參數設置進程是否共享某些數據,好比:

  • fork():建立子進程,經過調用0共享的clone,建立的進程是徹底複製父進程的數據,兩者不共享不可見。
  • pthread_create:經過調用最多共享的clone實現,就至關於通常意義上的線程了。

能夠看到Linus對進程與線程的觀點:
Linus的觀點,Re: proc fs and shared pids

相關文章
相關標籤/搜索