libssh2是一個C 函式館,用來實現SSH2協定。
基本介紹
- 中文名:libssh2
- 簡介:是一套安全通訊協定框架
- 產品:有openssh,putty
- 有關依賴庫:熟悉SSH2庫函式用法
簡介,參考用例,
簡介
SSH2是一套安全通訊協定框架(早期的SSH1由於存在安全漏洞),基於SSH2協定的產品主要有openssh,putty,SSH Secure Shell Client等,這些都是開源的,但是這些代碼非常難懂而且複雜,一個個函式深層次的調用很快就讓人在C語言代碼的海洋中迷失了方向,妄圖通過從這些開源軟體中抽取程式代碼段來“組裝”自己的應用程式是非一般人所能實現的。不過還好網路上出現了一些開源的SSH2開發庫,利用這些開發庫開發自己的SSH2程式卻要簡單得多,由於這些開發庫都是開源的,往往是針對linux平台的,而且一般只提供了原始碼。在windows上利用這些庫還必須要完成:編譯有關依賴庫-->編譯ssh2庫-->集成到開發環境(如Visual Studio)中-->熟悉SSH2庫函式用法-->開始編寫自己的程式.
參考用例
/**SampleshowinghowtodoSSH2connect.**Thesamplecodehasdefaultvaluesforhostname,username,password*andpathtocopy,butyoucanspecifythemonthecommandlinelike:**"ssh2hostuserpassword[-p|-i|-k]"*/#include"libssh2_config.h"#include<libssh2.h>#include<libssh2_sftp.h>#ifdef HAVE_WINDOWS_H#include<windows.h>#endif#ifdef HAVE_WINSOCK2_H#include<winsock2.h>#endif#ifdef HAVE_SYS_SOCKET_H#include<sys/socket.h>#endif#ifdef HAVE_NETINET_IN_H#include<netinet/in.h>#endif#ifdef HAVE_UNISTD_H#include<unistd.h>#endif#ifdef HAVE_ARPA_INET_H#include<arpa/inet.h>#endif#include<sys/types.h>#include<fcntl.h>#include<errno.h>#include<stdio.h>#include<ctype.h>const char* keyfile1="~/.ssh/id_rsa.pub";const char* keyfile2="~/.ssh/id_rsa";const char* username="username";const char* password="password";static void kbd_callback(const char* name,intname_len,const char* instruction,intinstruction_len,intnum_prompts,const LIBSSH2_USERAUTH_KBDINT_PROMPT* prompts,LIBSSH2_USERAUTH_KBDINT_RESPONSE* responses,void**abstract){(void)name;(void)name_len;(void)instruction;(void)instruction_len;if(num_prompts==1){responses[0].text=strdup(password);responses[0].length=strlen(password);}(void)prompts;(void)abstract;}/*kbd_callback*/int main(intargc,char* argv[]){unsigned long hostaddr;intrc,sock,i,auth_pw=0;struct sockaddr_insin;const char* fingerprint;char* userauthlist;LIBSSH2_SESSION* session;LIBSSH2_CHANNEL* channel;#ifdefWIN32WSADATA wsadata;WSAStartup(MAKEWORD(2,0),&wsadata);#endifif(argc>1){hostaddr=inet_addr(argv[1]);}else{hostaddr=htonl(0x7F000001);}if(argc>2){username=argv[2];}if(argc>3){password=argv[3];}rc=libssh2_init(0);if(rc!=0){fprintf(stderr,"libssh2initializationfailed(%d)\n",rc);return1;}/*Ultrabasic"connecttoport22onlocalhost".Yourcodeis*responsibleforcreatingthesocketestablishingtheconnection*/sock=socket(AF_INET,SOCK_STREAM,0);sin.sin_family=AF_INET;sin.sin_port=htons(22);sin.sin_addr.s_addr=hostaddr;if(connect(sock,(structsockaddr*)(&sin),sizeof(structsockaddr_in))!=0){fprintf(stderr,"failedtoconnect!\n");return-1;}/*Createasessioninstanceandstartitup.Thiswilltradewelcome*banners,exchangekeys,andsetupcrypto,compression,andMAClayers*/session=libssh2_session_init();if(libssh2_session_handshake(session,sock)){fprintf(stderr,"FailureestablishingSSHsession\n");return-1;}/*Atthispointwehavn'tauthenticated.Thefirstthingtodoischeck*thehostkey'sfingerprintagainstourknownhostsYourappmayhaveit*hardcoded,maygotoafile,maypresentittotheuser,that'syour*call*/fingerprint=libssh2_hostkey_hash(session,LIBSSH2_HOSTKEY_HASH_SHA1);fprintf(stderr,"Fingerprint:");for(i=0;i<20;i++){fprintf(stderr,"%02X",(unsignedchar)fingerprint[i]);}fprintf(stderr,"\n");/*checkwhatauthenticationmethodsareavailable*/userauthlist=libssh2_userauth_list(session,username,strlen(username));fprintf(stderr,"Authenticationmethods:%s\n",userauthlist);if(strstr(userauthlist,"password")!=NULL){auth_pw|=1;}if(strstr(userauthlist,"keyboard-interactive")!=NULL){auth_pw|=2;}if(strstr(userauthlist,"publickey")!=NULL){auth_pw|=4;}/*ifwegotan4.argumentwesetthisoptionifsupported*/if(argc>4){if((auth_pw&1)&&!strcasecmp(argv[4],"-p")){auth_pw=1;}if((auth_pw&2)&&!strcasecmp(argv[4],"-i")){auth_pw=2;}if((auth_pw&4)&&!strcasecmp(argv[4],"-k")){auth_pw=4;}}if(auth_pw&1){/*Wecouldauthenticateviapassword*/if(libssh2_userauth_password(session,username,password)){fprintf(stderr,"\tAuthenticationbypasswordfailed!\n");gotoshutdown;}else{fprintf(stderr,"\tAuthenticationbypasswordsucceeded.\n");}}elseif(auth_pw&2){/*Orviakeyboard-interactive*/if(libssh2_userauth_keyboard_interactive(session,username,&kbd_callback)){fprintf(stderr,"\tAuthenticationbykeyboard-interactivefailed!\n");gotoshutdown;}else{fprintf(stderr,"\tAuthenticationbykeyboard-interactivesucceeded.\n");}}elseif(auth_pw&4){/*Orbypublickey*/if(libssh2_userauth_publickey_fromfile(session,username,keyfile1,keyfile2,password)){fprintf(stderr,"\tAuthenticationbypublickeyfailed!\n");gotoshutdown;}else{fprintf(stderr,"\tAuthenticationbypublickeysucceeded.\n");}}else{fprintf(stderr,"Nosupportedauthenticationmethodsfound!\n");gotoshutdown;}/*Requestashell*/if(!(channel=libssh2_channel_open_session(session))){fprintf(stderr,"Unabletoopenasession\n");gotoshutdown;}/*Someenvironmentvariablesmaybeset,*It'suptotheserverwhichonesit'llallowthough*/libssh2_channel_setenv(channel,"FOO","bar");/*Requestaterminalwith'vanilla'terminalemulation*See/etc/termcapformoreoptions*/if(libssh2_channel_request_pty(channel,"vanilla")){fprintf(stderr,"Failedrequestingpty\n");gotoskip_shell;}/*OpenaSHELLonthatpty*/if(libssh2_channel_shell(channel)){fprintf(stderr,"Unabletorequestshellonallocatedpty\n");gotoshutdown;}/*Atthispointtheshellcanbeinteractedwithusing*libssh2_channel_read()*libssh2_channel_read_stderr()*libssh2_channel_write()*libssh2_channel_write_stderr()**Blockingmodemaybe(en|dis)abledwith:libssh2_channel_set_blocking()*IftheserversendEOF,libssh2_channel_eof()willreturnnon-0*TosendEOFtotheserveruse:libssh2_channel_send_eof()*Achannelcanbeclosedwith:libssh2_channel_close()*Achannelcanbefreedwith:libssh2_channel_free()*/skip_shell:if(channel){libssh2_channel_free(channel);channel=NULL;}/*Otherchanneltypesaresupportedvia:*libssh2_scp_send()*libssh2_scp_recv()*libssh2_channel_direct_tcpip()*/shutdown:libssh2_session_disconnect(session,"NormalShutdown,Thankyouforplaying");libssh2_session_free(session);#ifdefWIN32closesocket(sock);#elseclose(sock);#endiffprintf(stderr,"alldone!\n");libssh2_exit();return0;}