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
00030 #include "libts.h"
00031
00032
00033
00034
00035
00036
00037
00038
00039 #ifdef CHECK_PLAUSIBILITY_OF_SOCKADDR
00040 #define CHECK_PLAUSIBLE_SOCKADDR(_n,_f,_l) check_plausible_sockaddr(_n,_f,_n)
00041 inline void
00042 check_valid_sockaddr(sockaddr * sa, char *file, int line)
00043 {
00044 sockaddr_in *si = (sockaddr_in *) sa;
00045 unsigned short port = ntohs(si->sin_port);
00046 unsigned short addr = ntohl(si->sin_addr.s_addr);
00047
00048 if (port > 20000) {
00049 cerr << "[byteordering] In " << file << ", line " << line << " the IP port ";
00050 cerr << "was found to be " << port << "(in host byte order).\n";
00051 cerr << "[byteordering] This seems inplausible, so check for byte order problems\n";
00052 }
00053 }
00054 #else
00055 #define CHECK_PLAUSIBLE_SOCKADDR(_n,_f,_l)
00056 #endif
00057
00058 int
00059 safe_setsockopt(int s, int level, int optname, char *optval, int optlevel)
00060 {
00061 int r;
00062 do {
00063 r = setsockopt(s, level, optname, optval, optlevel);
00064 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00065 return r;
00066 }
00067
00068 int
00069 safe_getsockopt(int s, int level, int optname, char *optval, int *optlevel)
00070 {
00071 int r;
00072 do {
00073 r = getsockopt(s, level, optname, optval, (socklen_t *) optlevel);
00074 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00075 return r;
00076 }
00077
00078 int
00079 safe_fcntl(int fd, int cmd, int arg)
00080 {
00081 int r = 0;
00082 do {
00083 r = fcntl(fd, cmd, arg);
00084 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00085 return r;
00086 }
00087
00088 int
00089 safe_set_fl(int fd, int arg)
00090 {
00091 int flags = safe_fcntl(fd, F_GETFL, 0);
00092 if (flags < 0)
00093 return flags;
00094 flags |= arg;
00095 flags = safe_fcntl(fd, F_SETFL, flags);
00096 return flags;
00097 }
00098
00099 int
00100 safe_clr_fl(int fd, int arg)
00101 {
00102 int flags = safe_fcntl(fd, F_GETFL, 0);
00103 if (flags < 0)
00104 return flags;
00105 flags &= ~arg;
00106 flags = safe_fcntl(fd, F_SETFL, flags);
00107 return flags;
00108 }
00109
00110 int
00111 safe_nonblocking(int fd)
00112 {
00113 return safe_set_fl(fd, O_NONBLOCK);
00114 }
00115
00116 int
00117 safe_blocking(int fd)
00118 {
00119 return safe_clr_fl(fd, O_NONBLOCK);
00120 }
00121
00122 int
00123 write_ready(int fd)
00124 {
00125 struct pollfd p;
00126 p.events = POLLOUT;
00127 p.fd = fd;
00128 int r = poll(&p, 1, 0);
00129 if (r <= 0)
00130 return r;
00131 if (p.revents & (POLLERR | POLLNVAL))
00132 return -1;
00133 if (p.revents & (POLLOUT | POLLHUP))
00134 return 1;
00135 return 0;
00136 }
00137
00138 int
00139 read_ready(int fd)
00140 {
00141 struct pollfd p;
00142 p.events = POLLIN;
00143 p.fd = fd;
00144 int r = poll(&p, 1, 0);
00145 if (r <= 0)
00146 return r;
00147 if (p.revents & (POLLERR | POLLNVAL))
00148 return -1;
00149 if (p.revents & (POLLIN | POLLHUP))
00150 return 1;
00151 return 0;
00152 }
00153
00154 int
00155 safe_ioctl(int fd, int request, char *arg)
00156 {
00157 int r = -1;
00158 do {
00159 r = ioctl(fd, request, arg);
00160 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00161 return r;
00162 }
00163
00164 int
00165 safe_bind(int s, struct sockaddr const* name, int namelen)
00166 {
00167 int r;
00168 CHECK_PLAUSIBLE_SOCKADDR(name, __FILE__, __LINE__);
00169 do {
00170 r = bind(s, name, namelen);
00171 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00172 return r;
00173 }
00174
00175 int
00176 safe_listen(int s, int backlog)
00177 {
00178 int r;
00179 do {
00180 r = listen(s, backlog);
00181 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00182 return r;
00183 }
00184
00185 int
00186 safe_getsockname(int s, struct sockaddr *name, int *namelen)
00187 {
00188 int r;
00189 do {
00190 r = getsockname(s, name, (socklen_t *) namelen);
00191 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00192 return r;
00193 }
00194
00195 char
00196 fd_read_char(int fd)
00197 {
00198 char c;
00199 int r;
00200 do {
00201 r = read(fd, &c, 1);
00202 if (r > 0)
00203 return c;
00204 } while (r < 0 && (errno == EAGAIN || errno == EINTR));
00205 perror("fd_read_char");
00206 ink_assert(!"fd_read_char");
00207 return c;
00208 }
00209
00210 int
00211 fd_read_line(int fd, char *s, int len)
00212 {
00213 char c;
00214 int numread = 0, r;
00215
00216 do {
00217 do
00218 r = read(fd, &c, 1);
00219 while (r < 0 && (errno == EAGAIN || errno == EINTR));
00220
00221 if (r <= 0 && numread)
00222 break;
00223
00224 if (r <= 0)
00225 return r;
00226
00227 if (c == '\n')
00228 break;
00229
00230 s[numread++] = c;
00231 } while (numread < len - 1);
00232
00233 s[numread] = 0;
00234 return numread;
00235 }
00236
00237
00238 int
00239 close_socket(int s)
00240 {
00241 return close(s);
00242 }
00243
00244 int
00245 write_socket(int s, const char *buffer, int length)
00246 {
00247 return write(s, (const void *) buffer, length);
00248 }
00249
00250 int
00251 read_socket(int s, char *buffer, int length)
00252 {
00253 return read(s, (void *) buffer, length);
00254 }