source: benchmark/io/http/socket.cfa @ 7f0ac12

pthread-emulationqualifiedEnum
Last change on this file since 7f0ac12 was 7f0ac12, checked in by Thierry Delisle <tdelisle@…>, 6 months ago

First draft at acceptor thread webserver

  • Property mode set to 100644
File size: 1.9 KB
Line 
1#define _GNU_SOURCE
2
3#include "socket.hfa"
4
5#include <errno.h>
6#include <string.h>
7extern "C" {
8        #include <sys/socket.h>
9        #include <netinet/in.h>
10}
11
12#include <fstream.hfa>
13#include <time.hfa>
14#include <thread.hfa>
15
16#include "options.hfa"
17
18int prepaddr(struct sockaddr_in & address) {
19        int addrlen = sizeof(address);
20        memset( (char *)&address, '\0', addrlen );
21        address.sin_family = AF_INET;
22        address.sin_addr.s_addr = htonl(INADDR_ANY);
23        address.sin_port = htons( options.socket.port );
24        return addrlen;
25}
26
27int listener(struct sockaddr_in & address, int addrlen) {
28        int type = SOCK_STREAM;
29        if(options.socket.reuseport) type |= SOCK_NONBLOCK;
30        int sockfd = socket(AF_INET, type, 0);
31        if(sockfd < 0) {
32                abort( "socket error: (%d) %s\n", (int)errno, strerror(errno) );
33        }
34
35        if(options.socket.reuseport) {
36                int value = 1;
37                // if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (const void*)&on, sizeof(on)))
38                //      abort( "setsockopt SO_REUSEADDR error: (%d) %s\n", (int)errno, strerror(errno) );
39                if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEPORT, &value, sizeof(int)) < 0)
40                        abort( "setsockopt SO_REUSEPORT error: (%d) %s\n", (int)errno, strerror(errno) );
41        }
42
43        int ret = 0;
44        int waited = 0;
45        for() {
46                __CONST_SOCKADDR_ARG addr;
47                addr.__sockaddr__ = (struct sockaddr *)&address;
48                socklen_t addrlen = sizeof(address);
49                ret = bind( sockfd, addr, addrlen );
50                if(ret < 0) {
51                        if(errno == EADDRINUSE) {
52                                if(waited == 0) {
53                                        if(!options.interactive) abort | "Port already in use in non-interactive mode. Aborting";
54                                        sout | "Waiting for port";
55                                } else {
56                                        sout | "\r" | waited | nonl;
57                                        flush( sout );
58                                }
59                                waited ++;
60                                sleep( 1`s );
61                                continue;
62                        }
63                        abort( "bind error: (%d) %s\n", (int)errno, strerror(errno) );
64                }
65                break;
66        }
67
68        ret = listen( sockfd, options.socket.backlog );
69        if(ret < 0) {
70                abort( "listen error: (%d) %s\n", (int)errno, strerror(errno) );
71        }
72
73        return sockfd;
74}
Note: See TracBrowser for help on using the repository browser.