void http_server_init(unsigned short port, int (*POST_handler)(unsigned short data_index, unsigned short data_len), int (*TagExpand_handler) (char tagID, unsigned short pos,unsigned short len) ) { int socket; POST_CallBack = POST_handler; TagExpand_HTTP = TagExpand_handler; socket = tcp_socket_open(port, http_control_process); if (socket > 0) { printf("TCP Socket %d created, port %d\n", socket, tcp_get_port(socket)); }else { if (socket == TCP_INVALID_SOCKET) { printf("Error opening a socket: increment TCP_MAX_SOCKETS=%d\n", TCP_MAX_SOCKETS); } if (socket == TCP_PORT_ALREADY_USED) { printf("Error opening a socket: Port %d already used\n", port); } return; // Error } if (tcp_listen(socket) < 0) { printf("Error: socket %d can not put in LISTEN state\n", socket); return; // Error }else { printf("TCP Socket %d listening on Port %d\n", socket, tcp_get_port(socket)); } }
TCPSTREAM *tcp_open (char *host,char *service,unsigned long port) { TCPSTREAM *stream = NIL; int family; int sock = -1; int ctr = 0; int silent = (port & NET_SILENT) ? T : NIL; int *ctrp = (port & NET_NOOPENTIMEOUT) ? NIL : &ctr; char *s,*hostname,tmp[MAILTMPLEN]; void *adr; size_t adrlen; struct servent *sv = NIL; blocknotify_t bn = (blocknotify_t) mail_parameters (NIL,GET_BLOCKNOTIFY,NIL); void *data,*next; port &= 0xffff; /* erase flags */ /* lookup service */ if (service && (sv = getservbyname (service,"tcp"))) port = ntohs (sv->s_port); /* The domain literal form is used (rather than simply the dotted decimal as with other Unix programs) because it has to be a valid "host name" in mailsystem terminology. */ /* look like domain literal? */ if (host[0] == '[' && host[(strlen (host))-1] == ']') { strcpy (tmp,host+1); /* yes, copy number part */ tmp[(strlen (tmp))-1] = '\0'; if (adr = ip_stringtoaddr (tmp,&adrlen,&family)) { (*bn) (BLOCK_TCPOPEN,NIL); /* get an open socket for this system */ sock = tcp_socket_open (family,adr,adrlen,port,tmp,ctrp,hostname = host); (*bn) (BLOCK_NONE,NIL); fs_give ((void **) &adr); } else sprintf (tmp,"Bad format domain-literal: %.80s",host); } else { /* lookup host name */ if (tcpdebug) { sprintf (tmp,"DNS resolution %.80s",host); mm_log (tmp,TCPDEBUG); } (*bn) (BLOCK_DNSLOOKUP,NIL);/* quell alarms */ data = (*bn) (BLOCK_SENSITIVE,NIL); if (!(s = ip_nametoaddr (host,&adrlen,&family,&hostname,&next))) sprintf (tmp,"No such host as %.80s",host); (*bn) (BLOCK_NONSENSITIVE,data); (*bn) (BLOCK_NONE,NIL); if (s) { /* DNS resolution won? */ if (tcpdebug) mm_log ("DNS resolution done",TCPDEBUG); do { (*bn) (BLOCK_TCPOPEN,NIL); if (((sock = tcp_socket_open (family,s,adrlen,port,tmp,ctrp, hostname)) < 0) && (s = ip_nametoaddr (NIL,&adrlen,&family,&hostname,&next)) && !silent) mm_log (tmp,WARN); (*bn) (BLOCK_NONE,NIL); } while ((sock < 0) && s);/* repeat until success or no more addreses */ } } if (sock >= 0) { /* won */ stream = (TCPSTREAM *) memset (fs_get (sizeof (TCPSTREAM)),0, sizeof (TCPSTREAM)); stream->port = port; /* port number */ /* init sockets */ stream->tcpsi = stream->tcpso = sock; /* stash in the snuck-in byte */ if (stream->ictr = ctr) *(stream->iptr = stream->ibuf) = tmp[0]; /* copy official host name */ stream->host = cpystr (hostname); if (tcpdebug) mm_log ("Stream open and ready for read",TCPDEBUG); } else if (!silent) mm_log (tmp,ERROR); return stream; /* return success */ }
TCPSTREAM *tcp_open (char *host,char *service,unsigned long port) { TCPSTREAM *stream = NIL; int i,family; SOCKET sock = INVALID_SOCKET; int silent = (port & NET_SILENT) ? T : NIL; char *s,*hostname,tmp[MAILTMPLEN]; void *adr,*next; size_t adrlen; struct servent *sv = NIL; blocknotify_t bn = (blocknotify_t) mail_parameters (NIL,GET_BLOCKNOTIFY,NIL); if (!wsa_initted++) { /* init Windows Sockets */ WSADATA wsock; if (i = (int) WSAStartup (WINSOCK_VERSION,&wsock)) { wsa_initted = 0; /* in case we try again */ sprintf (tmp,"Unable to start Windows Sockets (%d)",i); mm_log (tmp,ERROR); return NIL; } } port &= 0xffff; /* erase flags */ /* lookup service */ if (service && (sv = getservbyname (service,"tcp"))) port = ntohs (sv->s_port); /* The domain literal form is used (rather than simply the dotted decimal as with other Windows programs) because it has to be a valid "host name" in mailsystem terminology. */ /* look like domain literal? */ if (host[0] == '[' && host[(strlen (host))-1] == ']') { strcpy (tmp,host+1); /* yes, copy number part */ tmp[strlen (tmp)-1] = '\0'; if (adr = ip_stringtoaddr (tmp,&adrlen,&family)) { (*bn) (BLOCK_TCPOPEN,NIL); sock = tcp_socket_open (family,adr,adrlen,(unsigned short) port,tmp, hostname = host); (*bn) (BLOCK_NONE,NIL); fs_give ((void **) &adr); } else sprintf (tmp,"Bad format domain-literal: %.80s",host); } else { /* lookup host name */ if (tcpdebug) { sprintf (tmp,"DNS resolution %.80s",host); mm_log (tmp,TCPDEBUG); } (*bn) (BLOCK_DNSLOOKUP,NIL);/* look up name */ if (!(s = ip_nametoaddr (host,&adrlen,&family,&hostname,&next))) sprintf (tmp,"Host not found (#%d): %s",WSAGetLastError (),host); (*bn) (BLOCK_NONE,NIL); if (s) { /* DNS resolution won? */ if (tcpdebug) mm_log ("DNS resolution done",TCPDEBUG); wsa_sock_open++; /* prevent tcp_abort() from freeing in loop */ do { (*bn) (BLOCK_TCPOPEN,NIL); if (((sock = tcp_socket_open (family,s,adrlen,(unsigned short) port, tmp,hostname)) == INVALID_SOCKET) && (s = ip_nametoaddr (NIL,&adrlen,&family,&hostname,&next)) && !silent) mm_log (tmp,WARN); (*bn) (BLOCK_NONE,NIL); } while ((sock == INVALID_SOCKET) && s); wsa_sock_open--; /* undo protection */ } } if (sock == INVALID_SOCKET) { /* do possible cleanup action */ if (!silent) mm_log (tmp,ERROR); tcp_abort (&sock); } else { /* got a socket, create TCP/IP stream */ stream = (TCPSTREAM *) memset (fs_get (sizeof (TCPSTREAM)),0, sizeof (TCPSTREAM)); stream->port = port; /* port number */ /* init socket */ stream->tcpsi = stream->tcpso = sock; stream->ictr = 0; /* init input counter */ /* copy official host name */ stream->host = cpystr (hostname); if (tcpdebug) mm_log ("Stream open and ready for read",TCPDEBUG); } return stream; /* return success */ }
TCPSTREAM *tcp_open (char *host,char *service,unsigned long port) { TCPSTREAM *stream = NIL; int i; int sock = -1; int ctr = 0; int silent = (port & NET_SILENT) ? T : NIL; int *ctrp = (port & NET_NOOPENTIMEOUT) ? NIL : &ctr; char *s; struct sockaddr_in sin; struct hostent *he; char hostname[MAILTMPLEN]; char tmp[MAILTMPLEN]; struct servent *sv = NIL; blocknotify_t bn = (blocknotify_t) mail_parameters (NIL,GET_BLOCKNOTIFY,NIL); void *data; port &= 0xffff; /* erase flags */ /* lookup service */ if (service && (sv = getservbyname (service,"tcp"))) port = ntohs (sin.sin_port = sv->s_port); /* copy port number in network format */ else sin.sin_port = htons (port); /* The domain literal form is used (rather than simply the dotted decimal as with other Amiga programs) because it has to be a valid "host name" in mailsystem terminology. */ /* look like domain literal? */ if (host[0] == '[' && host[(strlen (host))-1] == ']') { strcpy (hostname,host+1); /* yes, copy number part */ hostname[(strlen (hostname))-1] = '\0'; if ((sin.sin_addr.s_addr = inet_addr (hostname)) == -1) sprintf (tmp,"Bad format domain-literal: %.80s",host); else { sin.sin_family = AF_INET; /* family is always Internet */ strcpy (hostname,host); /* hostname is user's argument */ (*bn) (BLOCK_TCPOPEN,NIL); /* get an open socket for this system */ sock = tcp_socket_open (&sin,tmp,ctrp,hostname,port); (*bn) (BLOCK_NONE,NIL); } } else { /* lookup host name */ if (tcpdebug) { sprintf (tmp,"DNS resolution %.80s",host); mm_log (tmp,TCPDEBUG); } (*bn) (BLOCK_DNSLOOKUP,NIL);/* quell alarms */ data = (*bn) (BLOCK_SENSITIVE,NIL); if (!(he = gethostbyname (lcase (strcpy (hostname,host))))) sprintf (tmp,"No such host as %.80s",host); (*bn) (BLOCK_NONSENSITIVE,data); (*bn) (BLOCK_NONE,NIL); if (he) { /* DNS resolution won? */ if (tcpdebug) mm_log ("DNS resolution done",TCPDEBUG); /* copy address type */ sin.sin_family = he->h_addrtype; /* copy host name */ strcpy (hostname,he->h_name); #ifdef HOST_NOT_FOUND /* muliple addresses only on DNS systems */ for (sock = -1,i = 0; (sock < 0) && (s = he->h_addr_list[i]); i++) { if (i && !silent) mm_log (tmp,WARN); memcpy (&sin.sin_addr,s,he->h_length); (*bn) (BLOCK_TCPOPEN,NIL); sock = tcp_socket_open (&sin,tmp,ctrp,hostname,port); (*bn) (BLOCK_NONE,NIL); } #else /* the one true address then */ memcpy (&sin.sin_addr,he->h_addr,he->h_length); (*bn) (BLOCK_TCPOPEN,NIL); sock = tcp_socket_open (&sin,tmp,ctrp,hostname,port); (*bn) (BLOCK_NONE,NIL); #endif } } if (sock >= 0) { /* won */ stream = (TCPSTREAM *) memset (fs_get (sizeof (TCPSTREAM)),0, sizeof (TCPSTREAM)); stream->port = port; /* port number */ /* init sockets */ stream->tcpsi = stream->tcpso = sock; /* stash in the snuck-in byte */ if (stream->ictr = ctr) *(stream->iptr = stream->ibuf) = tmp[0]; /* copy official host name */ stream->host = cpystr (hostname); if (tcpdebug) mm_log ("Stream open and ready for read",TCPDEBUG); } else if (!silent) mm_log (tmp,ERROR); return stream; /* return success */ }