2016-08-30 95 views
1

我一直在通過C#編寫CLR書。我在第28章討論I/O綁定線程。什麼讓.NET任務在等待I/O完成後繼續?

這是我想我明白的:每個線程都有自己的堆棧。當您使用異步並一直等待(包括)您的IO時,系統會向設備的IRP隊列發送IO請求包(IRP)。一旦IO操作完成,完成的IRP又回到線程池「上」,並且線程池將資源分配給繼續運行,異步進程從停止。

我的問題是這樣的:當一個CLR線程把控制權交給一個IO設備時,那個CLR線程會發生什麼?該線程的堆棧是否全部彈出並返回到線程池?如果它被彈出來重用,那麼對於繼續等待IO完成的進程狀態來說,這不是那麼重要嗎?當IO完成時,計算機如何知道原始CLR線程在哪裏(按順序)? 它是怎麼知道在哪裏「撿回」它離開的地方

+0

哦,來吧,如果你要倒票,發表評論!我認爲這是一個很好的問題。 – Trevor

+0

該文檔(包括MSDN技術文章)是獲取有關這類內容的詳細信息的好地方。尤其是因爲在Windows中實際上有幾種不同的可用於異步I/O的機制,具體取決於您處理的具體I/O設備以及您使用的API。 –

+0

其中一種最常見的情況是使用I/O完成端口,其中創建了一些少量的線程並專用於等待IOCP。使用這種機制,單個線程可以爲大量操作提供I/O完成服務,從而有效地使用線程池。 –

回答

1

在CPU的某個地方有一個指針,記得「嘿,當你要求所有這個IO,你在程序邏輯中,這裏是你需要重新開始的地方」嗎?

不可以。異步I/O的恢復是通過一系列回調來完成的。 IOCP回調到在.NET I/O線程池線程上運行的完成例程,該例程(最終)完成Task,這會導致任務繼續運行,從而恢復執行async方法。欲瞭解更多信息,請參閱我的博客文章There Is No Thread

另外請注意,async方法做不是必然恢復在同一個線程。有關await如何在特定環境下恢復的更多信息,請參閱我的博客文章Async and Await

+0

謝謝斯蒂芬。我現在正在閱讀有關候補者和狀態機。我想這就是我想要的。我想揭示所有這些工作的「魔力」。很酷。 – Trevor

相關問題