comparison dbutil.c @ 293:9d110777f345 contrib-blacklist

propagate from branch 'au.asn.ucc.matt.dropbear' (head 7ad1775ed65e75dbece27fe6b65bf1a234db386a) to branch 'au.asn.ucc.matt.dropbear.contrib.blacklist' (head 1d86a4f0a401cc68c2670d821a2f6366c37af143)
author Matt Johnston <matt@ucc.asn.au>
date Fri, 10 Mar 2006 06:31:29 +0000
parents 044bc108b9b3
children 79bf1023cf11 973fccb59ea4 e17f0333c21e 28b10e93685c
comparison
equal deleted inserted replaced
247:c07de41b53d7 293:9d110777f345
151 fprintf(stderr, "\n"); 151 fprintf(stderr, "\n");
152 va_end(param); 152 va_end(param);
153 } 153 }
154 #endif /* DEBUG_TRACE */ 154 #endif /* DEBUG_TRACE */
155 155
156 /* Listen on address:port. Unless address is NULL, in which case listen on 156 static void set_sock_priority(int sock) {
157 * everything. If called with address == "", we'll listen on localhost/loopback. 157
158 int val;
159
160 /* disable nagle */
161 val = 1;
162 setsockopt(sock, IPPROTO_TCP, TCP_NODELAY, (void*)&val, sizeof(val));
163
164 /* set the TOS bit. note that this will fail for ipv6, I can't find any
165 * equivalent. */
166 #ifdef IPTOS_LOWDELAY
167 val = IPTOS_LOWDELAY;
168 setsockopt(sock, IPPROTO_IP, IP_TOS, (void*)&val, sizeof(val));
169 #endif
170
171 #ifdef SO_PRIORITY
172 /* linux specific, sets QoS class.
173 * 6 looks to be optimal for interactive traffic (see tc-prio(8) ). */
174 val = 6;
175 setsockopt(sock, SOL_SOCKET, SO_PRIORITY, (void*) &val, sizeof(val));
176 #endif
177
178 }
179
180 /* Listen on address:port.
181 * Special cases are address of "" listening on everything,
182 * and address of NULL listening on localhost only.
158 * Returns the number of sockets bound on success, or -1 on failure. On 183 * Returns the number of sockets bound on success, or -1 on failure. On
159 * failure, if errstring wasn't NULL, it'll be a newly malloced error 184 * failure, if errstring wasn't NULL, it'll be a newly malloced error
160 * string.*/ 185 * string.*/
161 int dropbear_listen(const char* address, const char* port, 186 int dropbear_listen(const char* address, const char* port,
162 int *socks, unsigned int sockcount, char **errstring, int *maxfd) { 187 int *socks, unsigned int sockcount, char **errstring, int *maxfd) {
172 197
173 memset(&hints, 0, sizeof(hints)); 198 memset(&hints, 0, sizeof(hints));
174 hints.ai_family = AF_UNSPEC; /* TODO: let them flag v4 only etc */ 199 hints.ai_family = AF_UNSPEC; /* TODO: let them flag v4 only etc */
175 hints.ai_socktype = SOCK_STREAM; 200 hints.ai_socktype = SOCK_STREAM;
176 201
177 if (address && address[0] == '\0') { 202 // for calling getaddrinfo:
203 // address == NULL and !AI_PASSIVE: local loopback
204 // address == NULL and AI_PASSIVE: all interfaces
205 // address != NULL: whatever the address says
206 if (!address) {
178 TRACE(("dropbear_listen: local loopback")) 207 TRACE(("dropbear_listen: local loopback"))
179 address = NULL;
180 } else { 208 } else {
181 TRACE(("dropbear_listen: not local loopback")) 209 if (address[0] == '\0') {
210 TRACE(("dropbear_listen: all interfaces"))
211 address = NULL;
212 }
182 hints.ai_flags = AI_PASSIVE; 213 hints.ai_flags = AI_PASSIVE;
183 } 214 }
184 err = getaddrinfo(address, port, &hints, &res0); 215 err = getaddrinfo(address, port, &hints, &res0);
185 216
186 if (err) { 217 if (err) {
221 setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (void*) &val, sizeof(val)); 252 setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (void*) &val, sizeof(val));
222 linger.l_onoff = 1; 253 linger.l_onoff = 1;
223 linger.l_linger = 5; 254 linger.l_linger = 5;
224 setsockopt(sock, SOL_SOCKET, SO_LINGER, (void*)&linger, sizeof(linger)); 255 setsockopt(sock, SOL_SOCKET, SO_LINGER, (void*)&linger, sizeof(linger));
225 256
226 /* disable nagle */ 257 set_sock_priority(sock);
227 setsockopt(sock, IPPROTO_TCP, TCP_NODELAY, (void*)&val, sizeof(val));
228 258
229 if (bind(sock, res->ai_addr, res->ai_addrlen) < 0) { 259 if (bind(sock, res->ai_addr, res->ai_addrlen) < 0) {
230 err = errno; 260 err = errno;
231 close(sock); 261 close(sock);
232 TRACE(("bind(%s) failed", port)) 262 TRACE(("bind(%s) failed", port))
345 snprintf(*errstring, len, "Error connecting: %s", strerror(err)); 375 snprintf(*errstring, len, "Error connecting: %s", strerror(err));
346 } 376 }
347 TRACE(("Error connecting: %s", strerror(err))) 377 TRACE(("Error connecting: %s", strerror(err)))
348 } else { 378 } else {
349 /* Success */ 379 /* Success */
350 /* (err is used as a dummy var here) */ 380 set_sock_priority(sock);
351 setsockopt(sock, IPPROTO_TCP, TCP_NODELAY, (void*)&err, sizeof(err));
352 } 381 }
353 382
354 freeaddrinfo(res0); 383 freeaddrinfo(res0);
355 if (sock > 0 && errstring != NULL && *errstring != NULL) { 384 if (sock > 0 && errstring != NULL && *errstring != NULL) {
356 m_free(*errstring); 385 m_free(*errstring);
557 } 586 }
558 587
559 } 588 }
560 #endif 589 #endif
561 590
562 /* loop until the socket is closed (in case of EINTR) or 591 /* make sure that the socket closes */
563 * we get and error. 592 void m_close(int fd) {
564 * Returns DROPBEAR_SUCCESS or DROPBEAR_FAILURE */
565 int m_close(int fd) {
566 593
567 int val; 594 int val;
568 do { 595 do {
569 val = close(fd); 596 val = close(fd);
570 } while (val < 0 && errno == EINTR); 597 } while (val < 0 && errno == EINTR);
571 598
572 if (val == 0 || errno == EBADF) { 599 if (val < 0 && errno != EBADF) {
573 return DROPBEAR_SUCCESS; 600 /* Linux says EIO can happen */
574 } else { 601 dropbear_exit("Error closing fd %d, %s", fd, strerror(errno));
575 return DROPBEAR_FAILURE;
576 } 602 }
577 } 603 }
578 604
579 void * m_malloc(size_t size) { 605 void * m_malloc(size_t size) {
580 606