我目前正在研究與SSH服務器交談的客戶端。 一切正常,但是,因爲服務器的回答很慢,所以我必須等待它發送數據。 我有兩種選擇,我想告訴你什麼是最有效的等待服務器的方式。使用sleep()或無限循環等待事件會更好嗎?
選擇#1:
while (!(ssh_channel_poll(*sshChannel,0)))
;
選擇#2:
while (!(ssh_channel_poll(*sshChannel,0)))
sleep(1);
我目前正在研究與SSH服務器交談的客戶端。 一切正常,但是,因爲服務器的回答很慢,所以我必須等待它發送數據。 我有兩種選擇,我想告訴你什麼是最有效的等待服務器的方式。使用sleep()或無限循環等待事件會更好嗎?
選擇#1:
while (!(ssh_channel_poll(*sshChannel,0)))
;
選擇#2:
while (!(ssh_channel_poll(*sshChannel,0)))
sleep(1);
兩種替代方法都是不可取的。通常情況下,你會使用阻塞讀取。我認爲它看起來是這樣的(因爲你說你正在等待服務器):
while (!ssh_channel_poll(...)) { ... }
ssh_channel_read(...);
在這種情況下,poll
是不必要的。只要確保SSH連接是阻止連接的,並且read
函數將等到數據可用,如果在調用時沒有可用的數據。
// This is all you need.
ssh_channel_read(...);
我最喜歡的方式是異步執行此操作。我調用一個async_read()函數,然後註冊一個調用async_read()函數的回調函數,該函數註冊相同的回調函數。這給你一個無限的阻塞循環。 – Stewart
@Stewart:我想你在想別的東西嗎?這個問題是關於libssh ... –
感謝您的答案。我應該更加明確:我使用ssh_channel_poll()調用來知道爲了存儲答案需要多少個字節給malloc()。如果我只使用ssh_channel_read(),我必須使用固定長度的緩衝區,但我不能確定它足夠大(除非我使用非常大的緩衝區,這不是我猜測的最好的緩衝區)。 – Chouchenn
你可能想調用poll(2)系統調用(或舊select(2)一個)。然後你需要獲得相關的文件描述符。或者使用ssh_channel_poll_timeout函數或ssh_channel_select。
我認爲使用sleep
而不是無限循環,因爲使用無限循環,你正在浪費CPU的功率和時間。當使用sleep
時,CPU將能夠運行其他程序。
CPU無論如何都可以運行其他程序,因爲該進程將被搶佔並且其優先級將降低。 –
所有的sleep()調用都是放棄時間片,並且使時序通常對於過程來說很奇怪。這意味着如果你在進入循環之後很快就讀了一些東西,你會在實際讀取之前產生一個奇怪的,任意的延遲,這是由sleep()引起的。這就是它所做的一切。 – Lundin
剪切不是一個好主意。 隨着睡眠(...)你幾乎不用你的cpu,像空的(...)。
那個ssh調用不是阻止嗎? –
@MartinJames它沒有。輪詢是阻止的替代方法。輪詢就像,「如果我**做了'read()',它會立即返回嗎?」 –
好吧,你也可以使用select(),http://man7.org/linux/man-pages/man2/select.2.html系統調用。 – LethalProgrammer