2011-03-17 116 views
1

我使用c#中的plink連接到Linux服務器並運行一些程序。 C#控制檯程序和plink.exe都在同一臺Windows機器上。如何對c#中plink的緩存關鍵問題做出回答yes

問題是,當我第一次連接到Linux服務器時,plink問我是否要接受並存儲來自Linux服務器的SSH密鑰。我總是想對此做出迴應,因爲所有的服務器都在我的局域網中,並且沒有安全問題。

我正在使用c#過程類型,將正確的參數傳遞給plink,重定向輸出並開始。現在問題是當plink提示時,process.StandardOutput.ReadToEnd();掛起,我無法確定我是否被plink提示接受密鑰或實際登錄到Linux服務器。

 string output = string.Empty; 
     string error = string.Empty; 
     string arguments = @" -ssh -pw password [email protected] ./Install_xxx.bin"; 

     using (Process process = new Process()) 
     { 
      ProcessStartInfo psi = new ProcessStartInfo(); 
      psi.FileName = "plink"; 
      psi.Arguments = arguments; 
      psi.ErrorDialog = false; 
      psi.UseShellExecute = false; 
      psi.RedirectStandardError = true; 
      psi.RedirectStandardInput = true; 
      psi.RedirectStandardOutput = true; 
      psi.CreateNoWindow = true; 

      process.StartInfo = psi; 
      process.Start(); 

      output = process.StandardOutput.ReadToEnd(); 
      error = process.StandardError.ReadToEnd(); 
     } 

感謝

回答

1

您的死鎖問題在Process文檔中有解釋。當進程等待輸入時,它不能關閉stdin,因此它會被阻塞。 StandardOutput將不會被關閉,因爲該進程仍在等待來自stdin的輸入:死鎖。 您可以使用異步apis逐行讀取,也可以使用另一個線程作爲其他流。

+0

謝謝...我決定使用異步方法。 – danze 2011-03-18 19:47:01

0

而不是使用外部可執行文件,使您的SSH連接,爲什麼不使用SSH庫,做到這一點(更可靠)通過代碼?

sharpSshmost recent version here)是Jsch的一個C#端口,它是BSD許可的Java庫。我非常成功地在C#項目中使用它;您將能夠以編程方式處理SSH連接的所有方面,包括密鑰協商。

0

爲了通過PLINK無縫連接到遠程服務器,第一次和隨後的時間,您必須手動協調您的SSH密鑰。也就是說,使用PUTTYGEN創建PLINK將使用的.ppk私鑰文件,並將相應的公鑰事先存儲在服務器上的~/.ssh/authorized_keys文件中。

您還需要協調的sshd的主機密鑰,所以使用的puttygen產生/etc/ssh下一套私有密鑰文件ssh_host_rsa_keyssh_host_dsa_key(看看現有的文件要弄清楚哪個鍵格式導出到),然後運行ssh-keygen -y -f /etc/ssh/ssh_host_rsa_key > /etc/ssh/ssh_host_rsa_key.pub創建相應的公鑰文件(同樣創建ssh_host_dsa_key.pub文件)。

如果您有多臺服務器要連接到,並且不介意使用同一個密鑰連接所有服務器(這將取決於您的本地IT安全策略),那麼只需複製相同的密鑰文件到每臺服務器上。

然後,在您使用PLINK的Windows計算機上,使用PUTTY或PLINK手動連接到任何服務器,並交互接受主機密鑰。一旦你這樣做了,PUTTY/PLINK將這些密鑰存儲在Windows註冊表中,位於HKCU\Software\SimonTatham\PuTTY\SshHostKeys之下。您會注意到像[email protected]:host這樣的條目,其中host是您服務器的主機名。現在

,對於程序的癥結所在,您需要將REG_SZ十六進制值0x23,...複製到C#應用程序,在那裏你必須手動使用Microsoft.Win32.RegistryKey類中使用相同的[email protected]:host編寫所有其他服務器這個值命名模式,然後再將其轉換爲PLINK(無論您認爲此註冊表值是否安全敏感取決於您,請在您的C#應用​​程序中以某種方式保護它,如果必須的話)。

與其他人一樣,您可能需要考慮使用SSH庫來獲得關於連接過程的更多程序化反饋,但要使用PLINK,這是您需要執行的操作。