2011-06-15 86 views
10

我對sched_yield函數有幾個問題,因爲我看到它在我的代碼中無法正常工作。很多時候,我發現同一個線程一次又一次地運行,即使在其他線程的情況下,當我試圖通過調用sched_yield來讓出它時。sched_yield的行爲

另外如果我有多核,所有內核或只有一個內核上運行的線程的產量將爲sched_yield。例如,我在線程1上運行線程1,2和3,在線程2上運行線程4,5和6,如果從線程2調用sched_yield,它將被線程1和3替換,還是僅替換爲1,3, 4,5和6都可能嗎?我在問這個問題,因爲在.Net Thread.Yield中,對於在同一核心/處理器上運行的線程只會產生收益。

+3

你打算如何運作? TBH,我不太明白爲什麼這個調用是有用的,無論是POSIX/*** X,Windows還是任何搶先式多任務處理器。如果你產生你的線程,你不能保證操作系統不會立即重新加載它,如果其他線程當時還沒有準備好,它們可能在同一個核心上。如果.NET版本具有處理器親和性(是的,我使用了它,它看起來像它),這甚至更奇怪 - 我想這可能會提高光纖性能? – 2011-06-15 13:43:08

+2

@MartinJames當你擁有比內核更多的可運行進程/線程,並且你想讓其他線程/進程有機會取得進展時(例如,一個線程剛剛給出了另一個線程要做的事情以及第一個線程在睡眠中等待完成比第二個線程執行「something」+第一個線程檢查它已完成)的成本要多 – jhfrontz 2013-11-27 13:55:42

回答

3

http://www.kernel.org/doc/man-pages/online/pages/man2/sched_yield.2.html

SCHED_YIELD()導致調用線程放棄對CPU。線程是 移動到隊列的末尾爲其靜態優先級和一個新的線程得到 運行。

如果調用線程是該 時間內最高優先級列表中的唯一線程,它將在調用sched_yield()後繼續運行。

sched_yield不是.Net調用,並且線程/進程模型與之不同。 Windows/.NET的調度程序與Linux的調度程序不一樣。 Linux甚至有幾個可能的調度程序。

因此,您對sched_yield的期望是錯誤的。

如果要控制線程的運行方式,可以將每個線程綁定到CPU。然後,線程只能在綁定的CPU上運行。如果你將有多個線程綁定到同一個CPU上,則sched_yield的使用可以切換到綁定到當前CPU並準備運行的另一個線程。

另外,如果每個線程都想要執行大量CPU密集型工作,那麼每個CPU使用多個線程可能是個壞主意。

如果您想獲得完全控制,如何運行線程,您可以使用實時線程。 http://www.linuxjournal.com/magazine/real-time-linux-kernel-scheduler - SCHED_FIFO和SCHED_RR RT策略。

-2

你爲什麼要放棄CPU?那麼...

我正在修復客戶端代碼中的錯誤。基本上,他們有一個共同的結構保持着信息:

  1. 多少硬幣中介 - 返回他們
  2. 多少票據中介 - 返回他們

以上是在過程中的A.其餘的代碼在進程B中。進程B向進程A發送消息以計算並返回託管中的資金(這是自動售貨機)。沒有進入,爲什麼代碼是這樣寫的歷史,原始的代碼序列是:

(工藝B) 發送消息RETURN_ESCROWED_BILLS方法A, 發送消息RETURN_ESCROWED硬幣方法A, 零出公共結構

這被作爲執行:

(方法B): 發送消息; 零結構;

(以後的過程A): 得到消息; 公用struct中的所有字段都是0; 無事可做;

哎呀...錢仍在託管,但過程A代碼已經失去了這種知識。真正需要(除了大規模重組代碼的其他)爲:

(方法B): 發送消息; 產生CPU;

(流程A): 確定託管貨幣並退貨; 產生CPU; (可能只是走到時間片的盡頭,不需要特殊的方法)

(處理B): 零公共結構;

任何時候你有IPC消息,發送/接收消息的進程都是緊密耦合最好的的方法是進行雙向握手。但是,有些情況下(通常是由於設計不佳或不存在),必須緊密耦合真正應該鬆散耦合的過程。 通常由於您沒有選擇,所以CPU的產量是一個破解。多核CPU的加入是一個痛苦的源頭,特別是從單核心移植到多核心時更是如此。

+1

這個回答是錯誤的sched_yield()不適用於進程間通信,也不會調用它來確保另一個線程實際運行,正如osgx所描述的那樣,這個想法是幫助操作系統有效地調度。 – uli 2015-06-23 11:14:50

+0

是的,sched_yield()對於進程間通信不是明確的,但是:發送線程需要放棄CPU以可預測的方式允許接收線程真正有機會獲得CPU,並且兩個進程的優先級相同,並且接收thr ead正在阻止,正在等待消息。否則,在發送任務丟失CPU和接收任務獲得CPU之間發生競爭。這種方法是可以預測的(Ubunto 8) – user2913342 2017-04-14 20:09:30