免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 10026 | 回复: 10
打印 上一主题 下一主题

再次求助(关于libssh2) [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2010-05-11 14:29 |只看该作者 |倒序浏览
本帖最后由 baidu9833 于 2010-05-11 14:30 编辑

快要崩溃了... 想破头 用了各种办法都无法解决 希望各位大侠不吝赐教啊
  1. /* purpose: to check out the functions of libssh2 */
  2. #include "libssh2_config.h"
  3. #include <libssh2.h>
  4. #include <libssh2_sftp.h>

  5. #ifdef HAVE_NETINET_IN_H
  6. #include <netinet/in.h>
  7. #endif

  8. #ifdef HAVE_SYS_SOCKET_H
  9. #include <sys/socket.h>
  10. #endif

  11. #ifdef HVAE_UNISTD_H
  12. #include <unistd.h>
  13. #endif

  14. #ifdef HAVE_ARPA_INET_H
  15. #include <arpa/inet.h>
  16. #endif

  17. #include <sys/types.h>
  18. #include <fcntl.h>
  19. #include <errno.h>
  20. #include <stdio.h>
  21. #include <ctype.h>

  22. const char * username = "username";
  23. const char * password = "password";
  24. const char * keyfile1 = "~/.ssh/id_rsa.pub";
  25. const char * keyfile2 = "~/.ssh/id_rsa";




  26. int main(int argc, char *argv[])
  27. {
  28.         /*初始化信息,包括主机地址,socket 临时变量等*/
  29.         unsigned long hostaddr;  /* to save host address */
  30.         int sock, i, rc, auth_pw = 0; /* socket, temporary save_id, and the type of authority */
  31.         struct sockaddr_in sin;
  32.         /*command 的初始值*/
  33.         char * command = "ls\n";
  34.         /*用于存放读取到的buf的变量*/
  35.         char  buf[1024];
  36.         memset(buf,0,1024);
  37.         const char * fingerprint ; /* I don't know what's this */
  38.         /*用于存放检测到的认证方式的变量*/
  39.         char *userauthlist;
  40.         /*会话*/
  41.         LIBSSH2_SESSION *session;
  42.         /*建立起的channel*/
  43.         LIBSSH2_CHANNEL *channel;

  44.         /*变量检测*/
  45.         if (argc > 1)
  46.         {
  47.                 hostaddr = inet_addr(argv[1]);
  48.         }
  49.         else
  50.         {
  51.                 hostaddr = htonl(0x7F000001);
  52.         }
  53.         if (argc > 2)
  54.         {
  55.                 username = argv[2];
  56.         }
  57.         if (argc > 3)
  58.         {
  59.                 password = argv[3];
  60.         }
  61.         if (argc > 4)
  62.         {
  63.                 command = argv[4];
  64.         }
  65.        

  66.         /*创建socket*/
  67.         sock = socket (AF_INET, SOCK_STREAM, 0);

  68. #ifndef WIN32
  69.         fcntl(sock,F_SETFL, 0);
  70. #endif

  71.         /*赋值ip信息*/
  72.         sin.sin_family = AF_INET;
  73.         sin.sin_port = htons(22);
  74.         sin.sin_addr.s_addr = hostaddr;
  75.        
  76.         /*连接服务器*/
  77.         if (connect(sock, (struct sockaddr*)(&sin),
  78.                                 sizeof(struct sockaddr_in)) != 0)
  79.         {
  80.                 fprintf(stderr, "failed to connect to the server!\n");
  81.                 return -1;
  82.         }
  83.         /*初始化会话*/
  84.         session = libssh2_session_init();
  85.        
  86.         /*创建会话*/
  87.         if (libssh2_session_startup(session, sock))
  88.         {
  89.                 fprintf(stderr, "Failure establishing SSH session\n");
  90.                 return -1;
  91.         }
  92.        
  93.         fingerprint = libssh2_hostkey_hash(session, LIBSSH2_HOSTKEY_HASH_MD5);
  94.         printf("Fingerprint: ");

  95.         for(i = 0; i < 16;i++)
  96.         {
  97.                 printf("%02X ", (unsigned char )fingerprint[i]);
  98.         }
  99.         printf("\n");
  100.         */
  101.         /*获得服务器端鉴权方式-- 一共三种 :密码,文件,键盘*/
  102.         userauthlist = libssh2_userauth_list(session, username, strlen(username));
  103.         printf("Authentication methods: %s\n",userauthlist);
  104.        
  105.         /*存在密码鉴权*/
  106.         if (strstr(userauthlist, "password") != NULL)
  107.         {
  108.                 auth_pw |= 1;
  109.         }
  110.         /*存在键盘鉴权*/
  111.         if (strstr(userauthlist, "keyboard-interactive") != NULL)
  112.         {
  113.                 auth_pw |= 2;
  114.         }       
  115.         /*存在文件鉴权*/
  116.         if (strstr(userauthlist, "publickey") != NULL)
  117.         {
  118.                 auth_pw |= 4;
  119.         }

  120.         /*密码鉴权*/
  121.         if (auth_pw & 1)
  122.         {
  123.                 if (libssh2_userauth_password(session, username, password))
  124.                 {
  125.                         printf("\tAuthentication by password failed!\n");
  126.                         goto shutdown;
  127.                 }
  128.                 else
  129.                 {
  130.                         printf("\tAuthentication by password succeeded.\n");
  131.                 }

  132.         }
  133.         /*文件鉴权,由于键盘方式比较麻烦,此处略去不计*/
  134.         else if (auth_pw & 4)
  135.         {
  136.                 if (libssh2_userauth_publickey_fromfile(session,username,keyfile1,keyfile2,password))
  137.                 {
  138.                         printf("\tAuthentication by public key failed! \n");
  139.                         goto shutdown;
  140.                 }
  141.                 else
  142.                 {
  143.                         printf("\tAuthentication by public key succeeded.\n");
  144.                 }
  145.         }
  146.         else
  147.         {
  148.                 printf("no supported authentication method founded!\n");
  149.                 goto shutdown;
  150.         }

  151.         /*创建一个通道*/
  152.         if (!(channel = libssh2_channel_open_session(session)))
  153.         {
  154.                 fprintf(stderr, "Unable to open a session\n");
  155.                 goto shutdown;
  156.         }
  157.         /*此处进行的虚拟终端初始化,需要*/
  158.         libssh2_channel_setenv(channel,"FOO","bar");

  159.         if (libssh2_channel_request_pty(channel,"vanilla"))
  160.         {
  161.                 fprintf(stderr,"Failed requesting pty\n");
  162.                 goto skip_shell;
  163.         }
  164.         /*此处隐去不用,经验证,不用它才能进行命令的发送,如果用它,那么就可以用读写的方式来进行交互*/
  165.        
  166.         if (libssh2_channel_shell(channel))
  167.         {
  168.                 fprintf(stderr,"Unable to request shell on allocated pty");
  169.                 goto shutdown;
  170.         }
  171.        
  172.        
  173.         /* now do our jobs */
  174.        
  175.         /*发送命令到对端*/       
  176.                         //rc = libssh2_channel_exec(channel,command);   
  177.                 rc = libssh2_channel_write(channel,command,strlen(command));
  178.                
  179.                
  180.                 /*
  181.                 if (rc != 0)
  182.                 {
  183.                         fprintf(stderr,"Failed to execute the command pty\n");
  184.                         goto shutdown;
  185.                 }
  186.                 */
  187.                 /*rc = libssh2_channel_read(channel,buf,1023);*/
  188.                 /*
  189.                 rc = libssh2_session_get_blocking(session);
  190.                 printf("before set ,status is %d\n",rc);
  191.                 libssh2_session_set_blocking(session, 0);
  192.                 rc = libssh2_session_get_blocking(session);
  193.                 printf("after set ,status is %d\n",rc);
  194.                 */
  195.                 /*以上是用来进行测试blocking*/
  196.                 /*读出通道里的buf(可能需要多次读取),并将其打印出来*/
  197.                
  198.                 rc = 1;
  199.                 while (rc > 0)
  200.                 {
  201.                         /* 如何对channel的buf进行检测 */
  202.                
  203.                         rc = libssh2_channel_read(channel,buf,1023);  /*就是此处,当ls命令执行完毕后,也就是channel中再无数据时,这时再去读取数据时会导致阻塞*/
  204.                         if (strstr(command,buf))
  205.                                 continue;
  206.                         fprintf(stderr,"%s\n",buf);
  207.                         memset(buf,0,1024);
  208.                 }
  209.                 fprintf(stderr,"Did I do read the buf? %d\n",rc);
  210.                
  211.                
  212. skip_shell:
  213.         if (channel)
  214.         {
  215.                 libssh2_channel_free(channel);
  216.                 channel = NULL;
  217.         }
  218. shutdown:
  219.         libssh2_session_disconnect(session, "Normal shutdown, Thank you \n");
  220.        
  221.         libssh2_session_free(session);
  222.        
  223.         close(sock);
  224. }
复制代码
各位,情况是这样的,我写了个测试程序,用来往服务器端发送对端可识别的命令 如代码中的 char * command = "ls\n"; 目的是当执行完毕后,服务端打印出执行结果,并且退出循环,结束工作。现在变成了 服务端打印完结果后,程序就阻塞在该读取的地方,不能返回,希望各位帮我看看 帮我解决下啊。

论坛徽章:
0
2 [报告]
发表于 2010-05-12 08:44 |只看该作者
自己往上顶

论坛徽章:
0
3 [报告]
发表于 2010-05-13 18:33 |只看该作者
继续往上顶

论坛徽章:
0
4 [报告]
发表于 2010-05-13 18:37 |只看该作者
又看见你了  haha

论坛徽章:
0
5 [报告]
发表于 2010-05-13 18:45 |只看该作者
你的服务端是系统的sshd还是自己写的

论坛徽章:
0
6 [报告]
发表于 2010-05-13 18:53 |只看该作者
If the server send EOF, libssh2_channel_eof() will return non-0
用libssh2_channel_eof()检查是不是结束了,不要设置为了非阻塞后就一个劲的傻读。

论坛徽章:
0
7 [报告]
发表于 2010-05-14 09:08 |只看该作者
你的服务端是系统的sshd还是自己写的
liangzhishao 发表于 2010-05-13 18:45


sshd 不是自己写的。系统带的

论坛徽章:
0
8 [报告]
发表于 2010-05-14 09:09 |只看该作者
If the server send EOF, libssh2_channel_eof() will return non-0
用libssh2_channel_eof()检查是不是结 ...
没本 发表于 2010-05-13 18:53

回这位仁兄:你的方法我试过了,不过不知道为什么检查不到~~ 怎么检查都返回0。。。

论坛徽章:
0
9 [报告]
发表于 2010-05-14 09:22 |只看该作者
ssh2有类似select这种东西吗

读之前要select呀

论坛徽章:
0
10 [报告]
发表于 2010-05-14 09:40 |只看该作者
ssh2有类似select这种东西吗

读之前要select呀
liangzhishao 发表于 2010-05-14 09:22



    貌似没有 所以才会很不解..
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP