network.c
上传用户:tany51
上传日期:2013-06-12
资源大小:1397k
文件大小:6k
源码类别:

MySQL数据库

开发平台:

Visual C++

  1. /*
  2.  * Copyright (C) 1998  Mark Baysinger (mbaysing@ucsd.edu)
  3.  * Copyright (C) 1998,1999,2000  Ross Combs (rocombs@cs.nmsu.edu)
  4.  *
  5.  * This program is free software; you can redistribute it and/or
  6.  * modify it under the terms of the GNU General Public License
  7.  * as published by the Free Software Foundation; either version 2
  8.  * of the License, or (at your option) any later version.
  9.  *
  10.  * This program is distributed in the hope that it will be useful,
  11.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13.  * GNU General Public License for more details.
  14.  *
  15.  * You should have received a copy of the GNU General Public License
  16.  * along with this program; if not, write to the Free Software
  17.  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
  18.  */
  19. #include "common/setup_before.h"
  20. #ifdef HAVE_STRING_H
  21. # include <string.h>
  22. #else
  23. # ifdef HAVE_STRINGS_H
  24. #  include <strings.h>
  25. # endif
  26. #endif
  27. #ifdef HAVE_UNISTD_H
  28. # include <unistd.h>
  29. #endif
  30. #include <errno.h>
  31. #include "compat/strerror.h"
  32. #ifdef HAVE_SYS_TYPES_H
  33. # include <sys/types.h>
  34. #endif
  35. #ifdef HAVE_SYS_SOCKET_H
  36. # include <sys/socket.h>
  37. #endif
  38. #include "compat/socket.h"
  39. #include "compat/recv.h"
  40. #include "compat/send.h"
  41. #ifdef HAVE_NETINET_IN_H
  42. # include <netinet/in.h>
  43. #endif
  44. #include "compat/netinet_in.h"
  45. #include "compat/psock.h"
  46. #include "common/packet.h"
  47. #include "common/eventlog.h"
  48. #include "common/field_sizes.h"
  49. #include "common/network.h"
  50. #include "common/setup_after.h"
  51. extern int net_recv_packet(int sock, t_packet * packet, unsigned int * currsize)
  52. {
  53.     int          addlen;
  54.     unsigned int header_size;
  55.     void *       temp;
  56.     
  57.     if (!packet)
  58.     {
  59. eventlog(eventlog_level_error,"net_recv_packet","[%d] got NULL packet (closing connection)",sock);
  60. return -1;
  61.     }
  62.     if (!currsize)
  63.     {
  64. eventlog(eventlog_level_error,"net_recv_packet","[%d] got NULL currsize (closing connection)",sock);
  65. return -1;
  66.     }
  67.     
  68.     if ((header_size = packet_get_header_size(packet))>=MAX_PACKET_SIZE)
  69.     {
  70. eventlog(eventlog_level_error,"net_recv_packet","[%d] could not determine header size (closing connection)",sock);
  71. return -1;
  72.     }
  73.     
  74.     if (!(temp = packet_get_raw_data_build(packet,*currsize)))
  75.     {
  76. eventlog(eventlog_level_error,"net_recv_packet","[%d] could not obtain raw data pointer at offset %u (closing connection)",sock,*currsize);
  77. return -1;
  78.     }
  79.     
  80.     if (*currsize<header_size)
  81.     {
  82. addlen = psock_recv(sock,
  83.             temp,
  84.             header_size-*currsize,
  85.             0);
  86.     }
  87.     else
  88.     {
  89. unsigned int total_size=packet_get_size(packet);
  90. if (total_size<header_size)
  91. {
  92.     eventlog(eventlog_level_warn,"net_recv_packet","[%d] corrupted packet received (total_size=%u currsize=%u) (closing connection)",sock,total_size,*currsize);
  93.     return -1;
  94. }
  95. if (*currsize>=total_size)
  96. {
  97.     eventlog(eventlog_level_warn,"net_recv_packet","[%d] more data requested for already complete packet (total_size=%u currsize=%u) (closing connection)",sock,total_size,*currsize);
  98.     return -1;
  99. }
  100. addlen = psock_recv(sock,
  101.             temp,
  102.             total_size-*currsize,
  103.             0);
  104.     }
  105.     
  106.     if (addlen==0)
  107.     {
  108. eventlog(eventlog_level_debug,"net_recv_packet","[%d] remote host closed connection",sock);
  109. return -1;
  110.     }
  111.     if (addlen<0)
  112.     {
  113.         if (
  114. #ifdef PSOCK_EINTR
  115.     psock_errno()==PSOCK_EINTR ||
  116. #endif
  117. #ifdef PSOCK_EAGAIN
  118.     psock_errno()==PSOCK_EAGAIN ||
  119. #endif
  120. #ifdef PSOCK_EWOULDBLOCK
  121.     psock_errno()==PSOCK_EWOULDBLOCK ||
  122. #endif
  123. #ifdef PSOCK_ENOMEM
  124.     psock_errno()==PSOCK_ENOMEM ||
  125. #endif
  126.     0) /* try later */
  127.             return 0;
  128. if (
  129. #ifdef PSOCK_ENOTCONN
  130.     psock_errno()==PSOCK_ENOTCONN ||
  131. #endif
  132. #ifdef PSOCK_ECONNRESET
  133.     psock_errno()==PSOCK_ECONNRESET ||
  134. #endif
  135.     0)
  136. {
  137. /*     eventlog(eventlog_level_debug,"net_recv_packet","[%d] remote host closed connection (psock_recv: %s)",sock,strerror(psock_errno())); */
  138.     return -1; /* common error: close connection, but no message */
  139. }
  140. eventlog(eventlog_level_error,"net_recv_packet","[%d] receive error (closing connection) (psock_recv: %s)",sock,strerror(psock_errno()));
  141. return -1;
  142.     }
  143.     
  144.     *currsize += addlen;
  145.     
  146.     if (*currsize>=header_size && *currsize==packet_get_size(packet))
  147. return 1;
  148.     
  149.     return 0;
  150. }
  151. extern int net_send_packet(int sock, t_packet const * packet, unsigned int * currsize)
  152. {
  153.     unsigned int size;
  154.     int          addlen;
  155.     
  156.     if (!packet)
  157.     {
  158. eventlog(eventlog_level_error,"net_send_packet","[%d] got NULL packet (closing connection)",sock);
  159. return -1;
  160.     }
  161.     if (!currsize)
  162.     {
  163. eventlog(eventlog_level_error,"net_send_packet","[%d] got NULL currsize (closing connection)",sock);
  164. return -1;
  165.     }
  166.     
  167.     if ((size = packet_get_size(packet))<1)
  168.     {
  169. eventlog(eventlog_level_error,"net_send_packet","[%d] packet to send is empty (skipping it)",sock);
  170. *currsize = 0;
  171. return 1;
  172.     }
  173.     
  174.     addlen = psock_send(sock,
  175.         packet_get_raw_data_const(packet,*currsize),
  176.         size-*currsize,
  177.         0);
  178.     
  179.     if (addlen<0)
  180.     {
  181. if (
  182. #ifdef PSOCK_EINTR
  183.     psock_errno()==PSOCK_EINTR ||
  184. #endif
  185. #ifdef PSOCK_EAGAIN
  186.     psock_errno()==PSOCK_EAGAIN ||
  187. #endif
  188. #ifdef PSOCK_EWOULDBLOCK
  189.     psock_errno()==PSOCK_EWOULDBLOCK ||
  190. #endif
  191. #ifdef PSOCK_ENOBUFS
  192.     psock_errno()==PSOCK_ENOBUFS ||
  193. #endif
  194. #ifdef PSOCK_ENOMEM
  195.     psock_errno()==PSOCK_ENOMEM ||
  196. #endif
  197.     0)
  198.     return 0; /* try again later */
  199. if (
  200. #ifdef PSOCK_EPIPE
  201.     psock_errno()!=PSOCK_EPIPE &&
  202. #endif
  203. #ifdef PSOCK_ECONNRESET
  204.     psock_errno()!=PSOCK_ECONNRESET &&
  205. #endif
  206.     1) eventlog(eventlog_level_error,"net_send_packet","[%d] could not send data (closing connection) (psock_send: %s)",sock,strerror(psock_errno()));
  207. return -1;
  208.     }
  209.     
  210.     if (addlen==0)
  211.     {
  212. eventlog(eventlog_level_error,"net_send_packet","[%d] no data sent (closing connection)",sock);
  213. return -1;
  214.     }
  215.     
  216.     *currsize += addlen;
  217.     
  218.     /* sent all data in this packet? */
  219.     if (size==*currsize)
  220.     {
  221. *currsize = 0;
  222. return 1;
  223.     }
  224.     
  225.     return 0;
  226. }