#include "server.h" #include "xmpp.h" #define HOST "im.celepar.parana" #define IP "10.15.20.219" #define PORT "5222" int tls = 0; void Read(void * fd, void *buf, int count) { bzero(buf, count); if ( tls == 0 ) read(*(int *) fd, buf, (ssize_t)count); else SSL_read((SSL *) fd, buf, count); } void Write(void * fd, void *buf, int count) { if ( tls == 0 ) write(*(int *) fd, buf, (ssize_t)count); else SSL_write((SSL *) fd, buf, count); } int main(int argc, char ** argv) { /* variables to parse arguments */ extern int optind, optopt; extern char * optarg; char * log_file; int c = (int)NULL, errflg = (int)NULL, verbose = (int)NULL, optval = 1; socklen_t optlen = sizeof(optval); /* fd -> file descriptor */ int socket_server_fd = (int)NULL, socket_server_port = (int)NULL, socket_accept_fd = (int)NULL, sockaddr_in_size = sizeof(struct sockaddr_in), err = (int)NULL; /* Internet socket address stuct */ struct sockaddr_in server_addr, accept_addr; struct client * clients = (struct client *) NULL, * current = (struct client *) NULL; pthread_t threads; /* clear screen */ system(__CLEAR_SCREEN__); while ( (c = getopt(argc, argv, ":vp:")) != -1 ) { switch ( c ) { case 'p': if ( socket_server_port = strtol(optarg, 0, 10) == 0 ) { fprintf(stderr, "Option -%c requires a valid port and '%s' isn't valid\n", optopt, optarg); ++errflg; } break; case 'v': verbose = 1; break; case ':': /* -f or -o without operand */ fprintf(stderr, "Option -%c requires an operand\n", optopt); ++errflg; break; case '?': fprintf(stderr, "Unrecognized option: -%c\n", optopt); ++errflg; } } if ( errflg ) { fprintf(stderr, "usage: . . . \n\n"); exit(2); } /* make a socket */ int one = 1; socket_server_fd = socket(AF_INET, SOCK_STREAM, 0); if ( socket_server_fd == __SOCKET_ERROR__ ) { printf("\nCould not make a socket\n"); return 0; } bzero((char *) &server_addr, sockaddr_in_size); bzero((char *) &accept_addr, sockaddr_in_size); if ( !socket_server_port ) socket_server_port = __DEFAULT_OPEN_PORT__; /* fill address struct */ server_addr.sin_addr.s_addr = INADDR_ANY; server_addr.sin_port = htons(socket_server_port); server_addr.sin_family = AF_INET; bzero(&(server_addr.sin_zero), 8); if ( __DEBUG__ || verbose ) printf("\nBinding to port %d...\n", socket_server_port); /* bind to a port */ if ( bind(socket_server_fd, (struct sockaddr *)&(server_addr), sizeof(server_addr)) == __SOCKET_ERROR__ ) { printf("\nCould not connect to host\n"); exit(1); } /* get port number */ getsockname(socket_server_fd, (struct sockaddr *)&(server_addr), (socklen_t *) &(sockaddr_in_size)); if ( __DEBUG__ || verbose ) { printf("\nopened socket as fd (%d) on port (%d) for stream i/o\n", socket_server_fd, ntohs(server_addr.sin_port)); printf("Server\n\ sin_family = %d\n\ sin_addr.s_addr = %d\n\ sin_port = %d\n" , server_addr.sin_family , server_addr.sin_addr.s_addr , ntohs(server_addr.sin_port) ); printf("\nMaking a listen queue of %d elements", __QUEUE_SIZE__); } /* establish listen queue */ if ( listen(socket_server_fd, __QUEUE_SIZE__) == __SOCKET_ERROR__ ) { printf("\nCould not listen\n"); return 0; } for ( ; ; ) { if ( __DEBUG__ || verbose ) puts("\nWaiting for a connection\n"); /* get the connected socket */ socket_accept_fd = accept(socket_server_fd, (struct sockaddr *) &(accept_addr), (socklen_t *) &(sockaddr_in_size)); fcntl(socket_accept_fd, F_SETFL, fcntl(socket_accept_fd, F_GETFL, 0) | O_NDELAY); if ( socket_accept_fd > -1 ) { if ( clients == (struct client *) NULL ) current = clients; else while ( (current = clients->next) != (struct client *) NULL ); current = (struct client *) malloc(sizeof(struct client)); current->next = (struct client *) NULL; current->fd = socket_accept_fd; current->sockaddr = accept_addr; current->last = time(NULL); pthread_create(&(threads), NULL, handler, (void *) current); } } pthread_exit(NULL); } void * handler(void * pClient) { char buffer_client[__BUFFER_SIZE__], buffer_jabber[__BUFFER_SIZE__]; struct client * client = (struct client *) pClient; int i = 0, err; time_t last; char ip[46]; unsigned short port; inet_ntop(AF_INET, &(client->sockaddr.sin_addr), ip, sizeof (ip)); port = ntohs(client->sockaddr.sin_port); printf("\nGot a connection from %s, port %hu\n", ip, port); /*---------------------------------------------------*/ int client_is_connected = -1; int jabber_is_connected = -1; struct sockaddr_in socketaddr; int socketfd, nHostPort; char buff[4096]; char * xml = (char)NULL; SSL_CTX *ctx; SSL *myssl; char * old_host, * replace_host; xml = (char *) malloc(sizeof(__CONNECT__)); if ( (nHostPort = strtol(PORT, 0, 10)) == 0 ) { printf("\n\n\n"); printf("\ncould not make a socket\n"); return 0; } socketfd = socket(AF_INET, SOCK_STREAM, 0); socketaddr.sin_family = AF_INET; socketaddr.sin_addr.s_addr = inet_addr(IP); socketaddr.sin_port = htons(nHostPort); OpenSSL_add_all_algorithms(); SSL_library_init(); SSL_load_error_strings(); if ( !(ctx = SSL_CTX_new(TLSv1_client_method())) ) { printf("Error creating the context.\n"); exit(0); } err = connect(socketfd, (struct sockaddr*)&socketaddr, sizeof(socketaddr)); fcntl(socketfd, F_SETFL, fcntl(socketfd, F_GETFL, 0) | O_NDELAY); if ( err < 0 ) { printf("Socket returned error #%d,program terminated\n", err); exit(0); } while ( client_is_connected != 0 ) { /* read from client */ puts("\tread - client"); bzero(buffer_client, __BUFFER_SIZE__); if ( (client_is_connected = read(client->fd, buffer_client, __BUFFER_SIZE__)) != 0 ) { if ( strlen(buffer_jabber) > 0 ) { puts("\twrite - client"); printf("\t%s\n", buffer_jabber); /* write in the client */ write(client->fd, buffer_jabber, strlen(buffer_jabber)); } if ( strstr(buffer_client, " 0 ) { puts("\twrite - jabber"); printf("\t%s\n", buffer_client); /* write in the jabber service */ write(socketfd, buffer_client, strlen(buffer_client)); } if ( strstr(buffer_jabber, "") ) { fcntl( socketfd, F_SETFL, fcntl( socketfd, F_GETFL ) & ~O_NDELAY ); SSL_CTX_set_verify(ctx,SSL_VERIFY_NONE,NULL); //Create new ssl object myssl=SSL_new(ctx); if(!myssl){ printf("Error creating SSL structure.\n"); exit(0); } //Bind the socket to the SSL structure SSL_set_fd(myssl,socketfd); //Connect to the server, SSL layer. err=SSL_connect(myssl); printf("SSL error #%d in accept,program terminated\n",err); //Check for error in connect. if (err<1) { err=SSL_get_error(myssl,err); printf("SSL error #%d in accept,program terminated\n",err); printf("%d -- %d\n\n", SSL_ERROR_WANT_READ, SSL_ERROR_WANT_WRITE); if(err==5){printf("sockerrno is:\n");} close(socketfd); SSL_CTX_free(ctx); exit(0); } fcntl(socketfd, F_SETFL, fcntl(socketfd, F_GETFL, 0) | O_NDELAY); } if ( jabber_is_connected == 0 ) client_is_connected = jabber_is_connected; puts("end loop"); usleep(500000); } if ( close(socketfd) == __SOCKET_ERROR__ ) { printf("\nCould not close jabber socket\n"); return 0; } //--------------------------------------------------- if ( close(client->fd) == __SOCKET_ERROR__ ) { printf("\nCould not close socket\n"); return 0; } fflush(stdin); fflush(stdout); free(client); pthread_exit(NULL); }