tcpip_device.c
00001
00002
00003
00004
00005
00006
00007 #include "tcpip_device.h"
00008 #include "connect_device.h"
00009 #include "detect_os.h"
00010 #include <stdlib.h>
00011 #ifdef NoSDL_Linux
00012 #include <sys/types.h>
00013 #include <sys/socket.h>
00014 #include <netinet/in.h>
00015 #include <arpa/inet.h>
00016 #include <sys/poll.h>
00017 #include <unistd.h>
00018 #include <stdio.h>
00019 #elif !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00020 #include <SDL_net.h>
00021 #endif
00022
00023
00024 #ifndef NoSDL_Linux
00025 static int Initialized = 0;
00026 #endif
00027 typedef struct {
00028 #ifdef NoSDL_Linux
00029 struct sockaddr_in address;
00030 struct pollfd nfds;
00031 #elif !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00032 TCPsocket socket;
00033 SDLNet_SocketSet set;
00034 #endif
00035 } ids_info_t;
00036 static ids_info_t ids[ID_MAX];
00037 static int last_id = 0;
00038
00039
00040 #ifndef NoSDL_Linux
00041 static void initTcpipDevice(void) {
00042 #if !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00043 if (SDLNet_Init() < 0) {
00044 return;
00045 }
00046 atexit(SDLNet_Quit);
00047 Initialized = 1;
00048 #endif
00049 }
00050 #endif
00051
00052
00057 int tcpip_open(const char *host, unsigned short port) {
00058 #ifdef NoSDL_Linux
00059 int len = sizeof(ids[0].address);
00060 int fd = socket(AF_INET, SOCK_STREAM, 0);
00061 int ret;
00062
00063 ids[last_id].nfds.fd = fd;
00064 ids[last_id].address.sin_family = AF_INET;
00065 ids[last_id].address.sin_addr.s_addr = inet_addr(host);
00066 ids[last_id].address.sin_port = htons(port);
00067
00068 ret = connect(fd, (struct sockaddr*)&ids[last_id].address, len);
00069 if (ret < 0) {
00070 perror("connect");
00071 return -1;
00072 }
00073
00074 ids[last_id].nfds.events = POLLIN | POLLPRI | POLLERR | POLLHUP | POLLNVAL;
00075 ids[last_id].nfds.revents = 0;
00076
00077 return last_id++;
00078
00079 #elif !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00080 IPaddress ip;
00081
00082 if (last_id >= ID_MAX) {
00083 return -1;
00084 }
00085 ids[last_id].socket = NULL;
00086 if (!Initialized) {
00087 initTcpipDevice();
00088 }
00089
00090 SDLNet_ResolveHost(&ip, host, port);
00091 ids[last_id].socket = SDLNet_TCP_Open(&ip);
00092 if (!ids[last_id].socket) {
00093 return DEVICE_OPEN_ERROR;
00094 }
00095
00096 ids[last_id].set = SDLNet_AllocSocketSet(1);
00097 SDLNet_TCP_AddSocket(ids[last_id].set, ids[last_id].socket);
00098
00099 return last_id++;
00100 #else
00101 return -1;
00102 #endif
00103 }
00104
00105
00106 void tcpip_close(int id) {
00107 #ifdef NoSDL_Linux
00108 #elif !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00109 if (ids[id].socket) {
00110 SDLNet_FreeSocketSet(ids[id].set);
00111 SDLNet_TCP_Close(ids[id].socket);
00112 ids[id].socket = NULL;
00113 }
00114 #endif
00115 }
00116
00117
00118 int tcpip_is_connected(int id) {
00119 #ifdef NoSDL_Linux
00120 return ids[id].nfds.fd >= 0;
00121 #elif !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00122 return (ids[id].socket) ? 1 : 0;
00123 #else
00124 return 0;
00125 #endif
00126 }
00127
00128
00129 int tcpip_recv(int id, char *data, int size, int timeout) {
00130 #ifdef NoSDL_Linux
00131 int fd = ids[id].nfds.fd;
00132 int filled = 0;
00133 int n;
00134
00135 while (filled < size) {
00136 if (poll(&ids[id].nfds, 1, timeout) == 0) {
00137 break;
00138 }
00139 n = read(fd, &data[filled], size - filled);
00140 if (n <= 0) {
00141 break;
00142 }
00143 filled += n;
00144 }
00145 return filled;
00146
00147 #elif !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00148 int n;
00149
00150 if (SDLNet_CheckSockets(ids[id].set, timeout) <= 0) {
00151 return 0;
00152 }
00153 if (SDLNet_SocketReady(ids[id].socket)) {
00154 n = SDLNet_TCP_Recv(ids[id].socket, data, size);
00155 if (n <= 0) {
00156 tcpip_close(id);
00157 return NO_CONNECT;
00158 }
00159 }
00160 return n;
00161 #else
00162 return 0;
00163 #endif
00164 }
00165
00166
00167 int tcpip_send(int id, const char *data, int length) {
00168 #ifdef NoSDL_Linux
00169 return write(ids[id].nfds.fd, data, length);
00170 #elif !HAVE_CONFIG_H || HAVE_LIBSDL_NET
00171 return SDLNet_TCP_Send(ids[id].socket, (char*)data, length);
00172 #else
00173 return 0;
00174 #endif
00175 }
00176