00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029 #include "precomp.h"
00030 #include "udp_socket.h"
00031 #include "event.h"
00032 #include "exception.h"
00033 #include "socket_event_handler.h"
00034 #ifdef WIN32
00035 #include <winsock.h>
00036 #define socklen_t int
00037 #else
00038 #include <sys/types.h>
00039 #include <sys/socket.h>
00040 #include <sys/time.h>
00041 #include <sys/types.h>
00042 #include <unistd.h>
00043 #include <netinet/in.h>
00044 #include <arpa/inet.h>
00045 #include <netdb.h>
00046 #endif
00047
00049
00050
00051 CL_UDPSocket::CL_UDPSocket()
00052 : handle(-1), socket_event_handler(0), read_event(0), write_event(0), exception_event(0)
00053 {
00054 handle = socket(PF_INET, SOCK_DGRAM, 0);
00055 if (handle == -1)
00056 throw CL_Exception(TEXT("Socket create failed"));
00057
00058 socket_event_handler = new CL_SocketEventHandler(handle);
00059 read_event = new CL_Event(socket_event_handler, CL_Event::type_socket_read);
00060 write_event = new CL_Event(socket_event_handler, CL_Event::type_socket_write);
00061 exception_event = new CL_Event(socket_event_handler, CL_Event::type_socket_exception);
00062 }
00063
00064 CL_UDPSocket::~CL_UDPSocket()
00065 {
00066 delete exception_event;
00067 delete write_event;
00068 delete read_event;
00069 delete socket_event_handler;
00070 #ifdef WIN32
00071 closesocket(handle);
00072 #else
00073 close(handle);
00074 #endif
00075 }
00076
00078
00079
00080 CL_Event *CL_UDPSocket::get_read_event()
00081 {
00082 return read_event;
00083 }
00084
00085 CL_Event *CL_UDPSocket::get_write_event()
00086 {
00087 return write_event;
00088 }
00089
00090 CL_Event *CL_UDPSocket::get_exception_event()
00091 {
00092 return exception_event;
00093 }
00094
00096
00097
00098 int CL_UDPSocket::send(const void *data, int len, const CL_IPAddress &to)
00099 {
00100 const sockaddr_in &name = to.get_sockaddr_v4();
00101 int res = ::sendto(handle, (const char *) data, len, 0, (const sockaddr *) &name, sizeof(sockaddr_in));
00102 if (res == -1)
00103 throw CL_Exception(TEXT("Write failed to socket!"));
00104 return res;
00105 }
00106
00107 int CL_UDPSocket::receive(void *data, int len, CL_IPAddress &from)
00108 {
00109 sockaddr_in &name = from.get_sockaddr_v4();
00110 memset(&name, 0, sizeof(sockaddr_in));
00111 name.sin_family = AF_INET;
00112
00113 socklen_t addr_len = sizeof(sockaddr_in);
00114 int res = recvfrom(handle, (char *) data, len, 0, (sockaddr *) &name, &addr_len);
00115 if (res == -1)
00116 throw CL_Exception(TEXT("Read failed on socket!"));
00117 return res;
00118 }
00119
00120 int CL_UDPSocket::peek(void *data, int len, CL_IPAddress &from, int timeout)
00121 {
00122 if (get_read_event()->wait(timeout) == false)
00123 return -1;
00124
00125 sockaddr_in &name = from.get_sockaddr_v4();
00126 memset(&name, 0, sizeof(sockaddr_in));
00127 name.sin_family = AF_INET;
00128
00129 socklen_t addr_len = sizeof(sockaddr_in);
00130 int res = recvfrom(handle, (char *) data, len, MSG_PEEK, (sockaddr *) &name, &addr_len);
00131 if (res == -1)
00132 throw CL_Exception(TEXT("Read failed on socket!"));
00133 return res;
00134 }
00135
00137