diff options
author | Jérémy Zurcher <jeremy@asynk.ch> | 2010-07-09 12:32:17 +0200 |
---|---|---|
committer | Jérémy Zurcher <jeremy@asynk.ch> | 2010-07-09 12:32:17 +0200 |
commit | 6c027b4de25a529908be895e7ff19236f4002a57 (patch) | |
tree | f70d3a400bbb9ba8a83e9d4ffcaa4b6e367fc8bb /cryptot.c | |
download | crypto-6c027b4de25a529908be895e7ff19236f4002a57.zip crypto-6c027b4de25a529908be895e7ff19236f4002a57.tar.gz |
initial commit, resurrect one of my realy old projects
Diffstat (limited to 'cryptot.c')
-rw-r--r-- | cryptot.c | 570 |
1 files changed, 570 insertions, 0 deletions
diff --git a/cryptot.c b/cryptot.c new file mode 100644 index 0000000..da565e1 --- /dev/null +++ b/cryptot.c @@ -0,0 +1,570 @@ +#include <netdb.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <sys/types.h> +#include <sys/socket.h> +#include <time.h> +#include <unistd.h> + +#include "cryptot.h" +#include "crypto_buffer.h" +#include "ipv4.h" +#include "scan.h" +#include "socket.h" + +#define HOSTLEN 64 /* length of hostname string in resolvip */ + +/* + * adding ciphers, fct to update : + * usage_cipher + * change_cipher + * allocate_buffer + * do_stats + */ + + +static void connect_to_dist(int sock, struct cryptot_st *data, int verbose) +{ + int retry = 5; + char buf[2]; + if(socket_local4(sock,data->local_ip,&data->local_port)==-1) + fprintf(stderr,"%s : socket_local4 error.\n",PROG_NAME); + if(verbose){ + fprintf(stderr,"%s : trying to connect to %03d.%03d.%03d.%03d:%d " + "from %03d.%03d.%03d.%03d:%d\n",PROG_NAME, + NIPQUAD(data->dist_ip),data->dist_port,NIPQUAD(data->local_ip),data->local_port); + } + while(retry--){ + if(!socket_connect4(sock,data->dist_ip,data->dist_port)){ + /* TODO we may be rejected by -S option */ + if(!recv(sock,buf,2,0)){ + fprintf(stderr,"%s : rejected (because of -S option ?).\n",PROG_NAME); exit(1); + } + if(strncmp(buf,"OK",2)) { + fprintf(stderr,"%s : protocol error (middle man ?).\n",PROG_NAME); exit(1); + } + if(verbose)fprintf(stderr,"%s : connected.\n",PROG_NAME); + return; + } + sleep(3); + fprintf(stderr,"%s : connect failed, retry\n",PROG_NAME); + } + fprintf(stderr,"%s socket_connect4 error :",PROG_NAME); + perror(""); + exit(1); +} + +static int wait_connection(int sock, struct cryptot_st *data, int verbose) +{ + int client; + char peer_ip[4]; + unsigned int peer_port; + + for(;;){ + if(verbose) + fprintf(stderr,"%s : waiting for a connection on %03d.%03d.%03d.%03d:%d.\n", + PROG_NAME, NIPQUAD(data->local_ip),data->local_port); + client = socket_accept4(sock,peer_ip,&peer_port); + if(client<0){ fprintf(stderr,"%s socket_accept error : ",PROG_NAME); perror(""); exit(1); } + + if(data->check_accept){ + if(peer_port != data->src_port || memcmp(data->src_ip,peer_ip,4)){ + fprintf(stderr,"%s : REFUSE connection from %03d.%03d.%03d.%03d:%d.\n", + PROG_NAME,NIPQUAD(peer_ip),peer_port); + shutdown(client,SHUT_RDWR); + close(client); + continue; + } + } + send(client,"OK",2,0); + if(verbose) + fprintf(stderr,"%s : accept connection from %03d.%03d.%03d.%03d:%d.\n", + PROG_NAME,NIPQUAD(peer_ip),peer_port); + return client; + } +} + +static void do_stats(struct cryptot_st *data, struct timespec *s0, struct timespec *s1, unsigned int count) +{ + char *cipher=NULL; + char b[6] = "bytes"; + char kb[3] = "Kb"; + char mb[3] = "Mb"; + char gb[3] = "Gb"; + char *unit = b; + float time; + int size =0; + float nbr =(float)count; + + if(nbr> 1024){ nbr/=1024; unit=kb;} + if(nbr> 1024){ nbr/=1024; unit=mb;} + if(nbr> 1024){ nbr/=1024; unit=gb;} + + time = (float)(s1->tv_sec - s0->tv_sec)+((float)(s1->tv_nsec-s0->tv_nsec))/1E9; + if (data->cipher & BLOWFISH) { cipher ="blowfish"; size = data->blocks*BF_BLOCK_SIZE;} + else if (data->cipher & TWOFISH) { cipher ="twofish"; size = data->blocks*TF_BLOCK_SIZE; } + else if (data->cipher & AES) { cipher ="aes"; size = data->blocks*AES_BLOCK_SIZE; } + else if (data->cipher & DES) { cipher ="des"; size = data->blocks*DES_BLOCK_SIZE; } + else if (data->cipher & DES3_EDE) { cipher ="des3_ede"; size = data->blocks*DES3_EDE_BLOCK_SIZE; } + fprintf(stderr,"\n%s statistics :\n",PROG_NAME); + fprintf(stderr,"\nusing %s cipher with a buffer of %d bytes.\n",cipher, size); + fprintf(stderr,"\n%.3f %s read in %0.2f second(s) ",nbr,unit,time); + fprintf(stderr,"=> %.3f %s/sec.\n",nbr/time,unit); +} + +static void usage(void) +{ + fprintf(stderr,"%s version %s, Copyright (C) 2004 Zurcher Jeremy\n",PROG_NAME,VERSION); + fprintf(stderr,"\tThis program is free software; you can redistribute it and/or modify\n"); + fprintf(stderr,"\tit under the terms of the GNU General Public License as published by\n"); + fprintf(stderr,"\tthe Free Software Foundation; either version 2 of the License, or\n"); + fprintf(stderr,"\t(at your option) any later version.\n"); + fprintf(stderr,"\tThis program is distributed in the hope that it will be useful,\n"); + fprintf(stderr,"\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n"); + fprintf(stderr,"\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n"); + fprintf(stderr,"\tGNU General Public License for more details.\n\n"); + + fprintf(stderr,"usage : %s [-v] [-x] [-c cipher] [-n nbr_blocks]\n" + " [-s [ip]:[port]] [-d [ip]:[port]] [-b [ip]:[port]] [-S [ip]:[port]] key\n",PROG_NAME); + fprintf(stderr,"\t\t-v : verbose mode (statistics)\n"); + fprintf(stderr,"\t\t-x : decrypt input (default is encrypt input)\n"); + fprintf(stderr,"\t\t-c cipher : -c h for help (default = blowfish)\n"); + fprintf(stderr,"\t\t-n nbr_blocks : nbr blocks in buffer (default = %d/CIPHER_BLOCK_SIZE)\n",BUFFER_LENGTH); + fprintf(stderr,"\t\t-s ip:port : local address to read from\n"); + fprintf(stderr,"\t\t-d ip:port : distant address to write to\n"); + fprintf(stderr,"\t\t-b ip:port : local address used for distant connection (use with -d option)\n"); + fprintf(stderr,"\t\t-S ip:port : distant address to accept connection from (use with -s option)\n"); + fprintf(stderr,"\t\t key : symetric secret key (see '-c h' for tips about key length)\n"); + fprintf(stderr,"\t\t MUST be the last argument of the command line.\n"); + fprintf(stderr,"\n"); + fprintf(stderr,"\twithout -s option reads input from stdin.\n"); + fprintf(stderr,"\twithout -d option writes output to stdout.\n"); + fprintf(stderr,"\twithout -S option accept connection from 'the first one'.\n"); + fprintf(stderr,"\n"); + fprintf(stderr,"\tif no ip is provided with s, d, b or S option, hostname is resolved and used.\n"); + fprintf(stderr,"\tif no port is provided with s, d, b or S option %d is used.\n",DEFAULT_PORT); + fprintf(stderr,"\n"); + fprintf(stderr,"\texample:\n\t\t%s -s :5000 -S 10.10.10.10:200 -d 10.10.10.10: -b : my_secret_key\n",PROG_NAME); + fprintf(stderr,"\t\twill listen on hostname:5000 for incoming data from 10.10.10.10:200, \n"); + fprintf(stderr,"\t\tencrypt it and send it to 10.10.10.10:%d through hostname:%d. \n",DEFAULT_PORT,DEFAULT_PORT); + fprintf(stderr,"\n"); + exit(1); +} + +static void usage_cipher(void) +{ + fprintf(stderr,"available ciphers :\n"); + fprintf(stderr,"\t0 : _Blowfish : A 64-Bit Block Cipher_ by Bruce Schneier...\n"); + fprintf(stderr,"\t1 : _Towfish : A 128-Bit Block Cipher_ by Bruce Schneier... (keylength : 16,24,32)\n"); + fprintf(stderr,"\t2 : _aes : A 128-Bit Block Cipher_ known as Rijndael... (keylength : 16,24,32)\n"); + fprintf(stderr,"\t3 : _des : A 64-Bit BLock Cipher_ improvement of Lucifer from IBM.. (keylength : 56)\n"); + fprintf(stderr,"\t4 : _des3_ede : Tripple des C = des_enc(des_dec(des_enc(M)))\n"); + fprintf(stderr,"\tnext to come : ??\n\n"); + exit(1); +} + +static void init_data(struct cryptot_st *data) +{ + data->key = NULL; + data->buffer = NULL; + data->size = -1; + data->blocks = -1; + data->cipher = DEFAULT_CIPHER; + data->check_accept = 0; + data->in_fd = 0; + data->out_fd = 1; + data->src_port = DEFAULT_PORT; + data->dist_port = DEFAULT_PORT; + data->local_port = DEFAULT_PORT; + data->src_ip[0] = data->src_ip[1] = data->src_ip[2] = data->src_ip[3] = 0; + data->dist_ip[0] = data->dist_ip[1] = data->dist_ip[2] = data->dist_ip[3] = 0; + data->local_ip[0] = data->local_ip[1] = data->local_ip[2] = data->local_ip[3] = 0; +} + +/* update cipher param */ +static void change_cipher(unsigned int *cipher, unsigned long param) +{ + *cipher &= DECRYPT; + if(param==0){ *cipher |= BLOWFISH; return ; } + if(param==1){ *cipher |= TWOFISH; return; } + if(param==2){ *cipher |= AES; return; } + if(param==3){ *cipher |= DES; return; } + if(param==4){ *cipher |= DES3_EDE; return; } + fprintf(stderr,"%s : unknown cipher.\n",PROG_NAME); + exit(1); +} + +/* set ip to localhost if == 0:0:0:0 */ +static void resolve_ip(char *ip) +{ + char hostname[HOSTLEN]; + struct hostent *hp; + + if(ip[0] == ip[1] && ip[1] == ip[2] && ip[2] == ip[3] && ip[3] == 0){ + if(gethostname(hostname,HOSTLEN)==-1){ + fprintf(stderr,"%s error ",PROG_NAME); + perror("gethostname "); exit(1); + } + if((hp = gethostbyname(hostname))==NULL){ + fprintf(stderr,"%s : can't resolve %s, ",PROG_NAME,hostname); + herror("\tgethostbyname "); exit(1); + } + memcpy(ip,hp->h_addr,4); + } +} + + +/* if ip is 0:0:0:0 use localhost, bind to ip/port call listen if required */ +static int bind_to(char *ip, int port, int listen) +{ + int socket; + + if((socket = socket_tcp(1))==-1) { fprintf(stderr,"%s error in ",PROG_NAME); perror("socket_tcp "); exit(1); } + + if(socket_bind4(socket,ip,port)==-1) { + fprintf(stderr,"%s : unable to bind to %03d.%03d.%03d.%03d:%d",PROG_NAME,NIPQUAD(*ip),port); + perror("\tsocket_bind "); exit(1); + } + + if(listen) if(socket_listen(socket,20)==-1) { + fprintf(stderr,"%s error in ",PROG_NAME); perror("socket_listen "); exit(1); + } + + return socket; +} + +/* compute blocks if == -1, allocate buffer, set size */ +static char* allocate_buffer(unsigned int cipher, unsigned int *blocks, unsigned int *size) +{ + char *buffer = NULL; + int tmp = *blocks; + + if(tmp==-1){ + if(cipher & BLOWFISH) tmp = BUFFER_LENGTH/BF_BLOCK_SIZE; + else if(cipher & TWOFISH) tmp = BUFFER_LENGTH/TF_BLOCK_SIZE; + else if(cipher & AES) tmp = BUFFER_LENGTH/AES_BLOCK_SIZE; + else if(cipher & DES) tmp = BUFFER_LENGTH/DES_BLOCK_SIZE; + else if(cipher & DES3_EDE) tmp = BUFFER_LENGTH/DES3_EDE_BLOCK_SIZE; + buffer = (char*)malloc(BUFFER_LENGTH); + } else { + if(cipher & BLOWFISH) buffer = (char*)malloc(tmp*BF_BLOCK_SIZE); + else if(cipher & TWOFISH) buffer = (char*)malloc(tmp*TF_BLOCK_SIZE); + else if(cipher & AES) buffer = (char*)malloc(tmp*AES_BLOCK_SIZE); + else if(cipher & DES) buffer = (char*)malloc(tmp*DES_BLOCK_SIZE); + else if(cipher & DES3_EDE) buffer = (char*)malloc(tmp*DES3_EDE_BLOCK_SIZE); + } + if(buffer==NULL) { fprintf(stderr,"%s : not enough memory for buffer.\n",PROG_NAME); exit(1); } + if(cipher & BLOWFISH) *size = tmp * BF_BLOCK_SIZE; + else if(cipher & TWOFISH) *size = tmp * TF_BLOCK_SIZE; + else if(cipher & AES) *size = tmp * AES_BLOCK_SIZE; + else if(cipher & DES) *size = tmp * DES_BLOCK_SIZE; + else if(cipher & DES3_EDE) *size = tmp * DES3_EDE_BLOCK_SIZE; + *blocks = tmp; + return buffer; +} + +static void c_encrypt(struct cryptot_st *data, int verbose) +{ + register unsigned int ret = 0; + register unsigned int reg = 0; + register unsigned int size = data->size; + register u8 *buffer = (u8*)data->buffer; + + operation op; + int input, output; + crypto_buffer c_buffer; + struct timespec s0, s1; + + input = data->in_fd; + output = data->out_fd; + + if(output==1) op = &u8_unix_write; + else{ + op = &u8_tcp_write; + connect_to_dist(output,data,verbose); + } + if(crypto_buffer_init(&c_buffer, output, op, data->blocks, data->cipher, (u8*)data->key, strlen(data->key))==-1){ + fprintf(stderr,"%s : crypto_buffer_init_error. Check your key len. (try -c h)\n",PROG_NAME); exit(1); + } + /* now I'm ready to write */ + + if(input==0){ + if(verbose){ + clock_gettime(MY_CLOCK, &s0); + while((ret=read(input, buffer, size))>0){ + reg += ret; + if(crypto_buffer_put(&c_buffer,buffer,ret)==-1){ + fprintf(stderr,"%s crypto_buffer_put error ",PROG_NAME); perror(""); exit(1); + } + } + } + else{ + reg = (unsigned int)&c_buffer; + while((ret=read(input, buffer, size))>0) + if(crypto_buffer_put((crypto_buffer*)reg,buffer,ret)==-1){ + fprintf(stderr,"%s crypto_buffer_put error ",PROG_NAME); perror(""); exit(1); + } + } + } else { + reg = wait_connection(input,data,verbose); + if(verbose){ + clock_gettime(MY_CLOCK, &s0); + while((ret=recv(reg, buffer, size, 0))>0){ + reg += ret; + if(crypto_buffer_put(&c_buffer,buffer,ret)==-1){ + fprintf(stderr,"%s crypto_buffer_put error ",PROG_NAME); perror(""); exit(1); + } + } + } + else{ + reg = (unsigned int)&c_buffer; + while((ret=recv(reg, buffer, size, 0))>0) + if(crypto_buffer_put((crypto_buffer*)reg,buffer,ret)==-1){ + fprintf(stderr,"%s crypto_buffer_put error ",PROG_NAME); perror(""); exit(1); + } + } + shutdown(reg,SHUT_RDWR); + close(reg); /* close client socket */ + } + crypto_buffer_flush(&c_buffer); + if(ret==-1){ fprintf(stderr,"%s read error ",PROG_NAME); perror(""); exit(1); } + if(verbose) { + clock_gettime(MY_CLOCK, &s1); + do_stats(data, &s0, &s1, reg); + } +} + +static void c_decrypt(struct cryptot_st *data, int verbose) +{ + register int n = 0; + register unsigned int ret = 0; + register unsigned int reg = 0; + register unsigned int size = data->size; + register u8 *buffer = (u8*)data->buffer; + + operation op; + int input, output; + crypto_buffer c_buffer; + struct timespec s0, s1; + + input = data->in_fd; + output = data->out_fd; + + if(input==0) op = &u8_unix_read; + else{ + op = &u8_tcp_read; + input = wait_connection(input,data,verbose); + } + if(crypto_buffer_init(&c_buffer, input, op, data->blocks, data->cipher, (u8*)data->key, strlen(data->key))==-1){ + fprintf(stderr,"%s : crypto_buffer_init_error. Check your key len. (try -c ?)\n",PROG_NAME); exit(1); + } + /* now I'm ready to read */ + + if(output==1){ + if(verbose){ + clock_gettime(MY_CLOCK, &s0); + while((ret=crypto_buffer_get(&c_buffer, buffer, size))>0){ + reg += ret; + n = write(output, buffer, ret); + } + } + else{ + reg = (unsigned int)&c_buffer; + while((ret=crypto_buffer_get(&c_buffer, buffer, size))>0) + n = write(output, buffer, ret); + } + } else { + connect_to_dist(output,data,verbose); + if(verbose){ + clock_gettime(MY_CLOCK, &s0); + while((ret=crypto_buffer_get(&c_buffer, buffer, size))>0){ + reg += ret; + if(send(output, buffer, ret, MSG_CONFIRM)==-1){ + fprintf(stderr,"%s send error ",PROG_NAME); perror(""); exit(1); + } + } + } + else{ + reg = (unsigned int)&c_buffer; + while((ret=crypto_buffer_get(&c_buffer, buffer, size))>0) + if(send(output, buffer, ret, MSG_CONFIRM)==-1){ + fprintf(stderr,"%s send error ",PROG_NAME); perror(""); exit(1); + } + } + + } + if(input!=0) { shutdown(input,SHUT_RDWR); close(input); } /* close client socket */ + if(ret==-1){ fprintf(stderr,"%s read error ",PROG_NAME); perror(""); exit(1); } + if(verbose) { + clock_gettime(MY_CLOCK, &s1); + do_stats(data, &s0, &s1, reg); + } +} + +static void argument_error(char opt, int wrong) +{ + if(wrong) fprintf(stderr,"%s : -%c option, wrong argument.\n",PROG_NAME,opt); + else fprintf(stderr,"%s : -%c option, argument missing.\n",PROG_NAME,opt); + exit(1); +} + +int main(int argc, char **argv) +{ + /* general */ + int ret; + char *tmp; + unsigned long param; + unsigned int verbose = 0; + char bind_ip[4]; + unsigned int bind_port; + + /* crypto */ + struct cryptot_st data; + + init_data(&data); + bind_ip[0] = bind_ip[1] = bind_ip[2] = bind_ip[3] = 0; + bind_port = DEFAULT_PORT; + + if(!--argc) usage(); + ++argv; + while(argc--){ + if((*argv)[0]=='-'){ + if((*argv)[1]=='v') verbose = 1; + + else if((*argv)[1]=='x') data.cipher|=DECRYPT; + + else if((*argv)[1]=='n') { + if(!argc--) argument_error('n',0); + ret=scan_ulong(*(++argv),¶m); + if(!ret || (*argv)[ret]) argument_error('n',1); + data.blocks = (unsigned int)param; + } + + else if((*argv)[1]=='c') { + if(!argc--) argument_error('c',0); + if(*(*(++argv))=='h') usage_cipher(); + ret=scan_ulong(*argv,¶m); + if(!ret || (*argv)[ret])argument_error('c',1); + change_cipher(&data.cipher,param); + } + + else if((*argv)[1]=='s') { + if(!argc--) argument_error('s',0); + ret=ipv4_scan(*(++argv),data.local_ip); + tmp = &(*argv)[ret]; + if(*tmp++!=':') argument_error('s',1); + ret=scan_ulong(tmp,¶m); + if(ret) data.local_port = (unsigned int)param; + if(*(tmp+ret)) argument_error('s',1); + data.in_fd = -1; + } + + else if((*argv)[1]=='b') { + if(!argc--) argument_error('b',0); + ret=ipv4_scan(*(++argv),bind_ip); + tmp = &(*argv)[ret]; + if(*tmp++!=':') argument_error('b',1); + ret=scan_ulong(tmp,¶m); + if(ret) bind_port = (unsigned int)param; + if(*(tmp+ret)) argument_error('b',1); + } + + else if((*argv)[1]=='d') { + if(!argc--) argument_error('d',0); + ret=ipv4_scan(*(++argv),data.dist_ip); + tmp = &(*argv)[ret]; + if(*tmp++!=':') argument_error('d',1); + ret=scan_ulong(tmp,¶m); + if(ret) data.dist_port = (unsigned int)param; + if(*(tmp+ret)) argument_error('d',1); + data.out_fd = -1; + } + + else if((*argv)[1]=='S') { + if(!argc--) argument_error('S',0); + ret=ipv4_scan(*(++argv),data.src_ip); + tmp = &(*argv)[ret]; + if(*tmp++!=':') argument_error('S',1); + ret=scan_ulong(tmp,¶m); + if(ret) data.src_port = (unsigned int)param; + if(*(tmp+ret)) argument_error('S',1); + data.check_accept = 1; + } + else usage(); + } + else { data.key = *argv; break; } + argv++; + } + if(!data.key) usage(); + + /* if ip is 0:0:0:0 call gethostname and gethostbyname */ + if(data.in_fd != 0) resolve_ip(data.local_ip); + if(data.out_fd != 1){ resolve_ip(data.dist_ip); resolve_ip(bind_ip); } + if(data.in_fd != 0 && data.check_accept) resolve_ip(data.src_ip); + + /* if input AND output have been changed, check that local != bind AND local != distant */ + if(data.in_fd != 0 && data.out_fd != 1){ + if(data.local_port == bind_port && !memcmp(data.local_ip,bind_ip,4)){ + fprintf(stderr,"%s : trying to bind twice to same address; use -b option.\n",PROG_NAME); + exit(1); + } + if(data.local_port == data.dist_port && !memcmp(data.local_ip,data.dist_ip,4)){ + fprintf(stderr,"%s : trying to read from output, you crazy !\n",PROG_NAME); + exit(1); + } + } + + if(data.in_fd != 0) data.in_fd = bind_to(data.local_ip, data.local_port, 1); /* bind and listen */ + if(data.out_fd != 1) data.out_fd = bind_to(bind_ip, bind_port, 0); /* bind */ + + data.buffer = allocate_buffer(data.cipher, &data.blocks, &data.size); /* allocate buffer and set blocks & size */ + +#ifdef _DEBUG_ + fprintf(stderr,"user defind aprameters :\n"); + fprintf(stderr,"\tcipher : %d\n",data.cipher); + fprintf(stderr,"\tblocks : %d\n",data.blocks); + fprintf(stderr,"\tsize : %d\n",data.size); + fprintf(stderr,"\tkey : %s\n",data.key); + fprintf(stderr,"\tlocal %03d.%03d.%03d.%03d:%d\n", + NIPQUAD(data.local_ip),data.local_port); + fprintf(stderr,"\tdist %03d.%03d.%03d.%03d:%d\n", + NIPQUAD(data.dist_ip),data.dist_port); + fprintf(stderr,"\tbind %03d.%03d.%03d.%03d:%d\n", + NIPQUAD(bind_ip),bind_port); + fprintf(stderr,"\tsrc %03d.%03d.%03d.%03d:%d\n", + NIPQUAD(src_ip),src_port); +#endif + + if(verbose){ + fprintf(stderr,"%s : running in verbose mode:\n",PROG_NAME); + if(data.in_fd !=0){ + socket_local4(data.in_fd,data.local_ip,&data.local_port); + fprintf(stderr,"%s : reading from : %03d.%03d.%03d.%03d:%d\n", + PROG_NAME,NIPQUAD(data.local_ip),data.local_port); + if(data.check_accept) fprintf(stderr,"%s : accept connection from : %03d.%03d.%03d.%03d:%d\n", + PROG_NAME,NIPQUAD(data.src_ip),data.src_port); + else fprintf(stderr,"%s : accept connection from anywhere.\n",PROG_NAME); + } + else fprintf(stderr,"%s : reading from stdin\n",PROG_NAME); + if(data.out_fd !=1){ + socket_local4(data.out_fd,data.local_ip,&data.local_port); + fprintf(stderr,"%s : writing through to : %03d.%03d.%03d.%03d:%d\n", + PROG_NAME,NIPQUAD(data.local_ip),data.local_port); + } + else fprintf(stderr,"%s : writing to stdout\n",PROG_NAME); + } + + if(data.cipher&DECRYPT){ + c_decrypt(&data,verbose); + } + else{ + c_encrypt(&data,verbose); + } + + /* close sockets */ + if(data.in_fd !=0) close(data.in_fd); + if(data.out_fd !=0) close(data.out_fd); + + return 0; +} |