From b513584fdb19fc5067c047658bca45dd360c4e3b Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 8 Mar 2016 12:43:07 +0300 Subject: [PATCH 01/38] More distinct error codes for SOCKS --- src/socks.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/socks.c b/src/socks.c index 16a98b0..31c09d8 100644 --- a/src/socks.c +++ b/src/socks.c @@ -121,7 +121,7 @@ void * sockschild(struct clientparam* param) { } #endif if(SAISNULL(¶m->req)) { - RETURN(421); + RETURN(431); } myinet_ntop(*SAFAMILY(¶m->sinsr), SAADDR(¶m->sinsr), (char *)buf, 64); break; @@ -164,7 +164,7 @@ void * sockschild(struct clientparam* param) { } *SAPORT(¶m->sinsr) = *SAPORT(¶m->req) = port; - if(command == 1 && !*SAPORT(¶m->sinsr)) {RETURN(421);} + if(command == 1 && !*SAPORT(¶m->sinsr)) {RETURN(461);} switch(command) { case 1: param->operation = CONNECT; From a44a32c484af97e54866102910fcbbc413f74905 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 8 Mar 2016 13:28:29 +0300 Subject: [PATCH 02/38] Do not fail for zero address on SOCKSv5 BIND/UDPASSOC --- src/socks.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/socks.c b/src/socks.c index 31c09d8..4d048f8 100644 --- a/src/socks.c +++ b/src/socks.c @@ -120,7 +120,7 @@ void * sockschild(struct clientparam* param) { #ifndef NOIPV6 } #endif - if(SAISNULL(¶m->req)) { + if(command == 1 && SAISNULL(¶m->req)) { RETURN(431); } myinet_ntop(*SAFAMILY(¶m->sinsr), SAADDR(¶m->sinsr), (char *)buf, 64); From f67c9a39f1c11cfdef283129333e891fdf018cbb Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 9 Mar 2016 18:28:52 +0300 Subject: [PATCH 03/38] Use setreuid/setregid instead of setuid / setgid --- src/conf.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/conf.c b/src/conf.c index 9b3239f..0877803 100644 --- a/src/conf.c +++ b/src/conf.c @@ -1293,7 +1293,7 @@ static int h_plugin(int argc, unsigned char **argv){ static int h_setuid(int argc, unsigned char **argv){ int res; res = atoi((char *)argv[1]); - if(!res || setuid(res)) { + if(!res || setreuid(res,res)) { fprintf(stderr, "Unable to set uid %d", res); return(1); } @@ -1304,7 +1304,7 @@ static int h_setgid(int argc, unsigned char **argv){ int res; res = atoi((char *)argv[1]); - if(!res || setgid(res)) { + if(!res || setregid(res,res)) { fprintf(stderr, "Unable to set gid %d", res); return(1); } From dcec2cadaa6ae1aaf9fb9d037ec1782ee3003526 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Thu, 10 Mar 2016 17:05:56 +0300 Subject: [PATCH 04/38] support external username / password up to 128 octets --- src/auth.c | 2 +- src/ftp.c | 10 +++++----- src/ftppr.c | 2 +- src/pop3p.c | 2 +- src/proxy.c | 4 ++-- src/smtpp.c | 2 +- 6 files changed, 11 insertions(+), 11 deletions(-) diff --git a/src/auth.c b/src/auth.c index 05c9e2e..83a7d82 100644 --- a/src/auth.c +++ b/src/auth.c @@ -57,7 +57,7 @@ int clientnegotiate(struct chain * redir, struct clientparam * param, struct soc ":%hu HTTP/1.0\r\nProxy-Connection: keep-alive\r\n", ntohs(*SAPORT(addr))); if(user){ len += sprintf((char *)buf + len, "Proxy-authorization: basic "); - sprintf((char *)username, "%.128s:%.64s", user, pass?pass:(unsigned char *)""); + sprintf((char *)username, "%.128s:%.128s", user, pass?pass:(unsigned char *)""); en64(username, buf+len, (int)strlen((char *)username)); len = (int)strlen((char *)buf); len += sprintf((char *)buf + len, "\r\n"); diff --git a/src/ftp.c b/src/ftp.c index b776115..3007ade 100644 --- a/src/ftp.c +++ b/src/ftp.c @@ -9,17 +9,17 @@ int ftplogin(struct clientparam *param, char *nbuf, int *innbuf) { - char tbuf[1024]; + char tbuf[256]; int i; char *buf; int len; int res; buf = nbuf?nbuf:tbuf; - len = nbuf?*innbuf:1024; + len = nbuf?*innbuf:sizeof(tbuf); if(innbuf)*innbuf = 0; - if(len < 48) return 707; + if(len < 140) return 707; while((i = sockgetlinebuf(param, SERVER, (unsigned char *)buf, len - 1, '\n', conf.timeouts[STRING_L])) > 0 && (i < 3 || !isnumber(*buf) || buf[3] == '-')){ } if(i < 3) return 706; @@ -28,7 +28,7 @@ int ftplogin(struct clientparam *param, char *nbuf, int *innbuf) { *innbuf = i; return 702; } - sprintf(buf, "USER %.32s\r\n", param->extusername?param->extusername:(unsigned char *)"anonymous"); + sprintf(buf, "USER %.128s\r\n", param->extusername?param->extusername:(unsigned char *)"anonymous"); if((int)socksend(param->remsock, (unsigned char *)buf, (int)strlen(buf), conf.timeouts[STRING_S]) != (int)strlen(buf)){ return 703; } @@ -40,7 +40,7 @@ int ftplogin(struct clientparam *param, char *nbuf, int *innbuf) { buf[i] = 0; res = atoi(buf)/100; if(res == 3){ - sprintf(buf, "PASS %.32s\r\n", + sprintf(buf, "PASS %.128s\r\n", param->extusername? (param->extpassword? param->extpassword:(unsigned char *)"") diff --git a/src/ftppr.c b/src/ftppr.c index 820e9cc..0cc0762 100644 --- a/src/ftppr.c +++ b/src/ftppr.c @@ -70,7 +70,7 @@ void * ftpprchild(struct clientparam* param) { param->res = res; if(inbuf && inbuf != BUFSIZE && socksend(param->ctrlsock, buf, inbuf, conf.timeouts[STRING_S])!=inbuf) {RETURN (807);} if(!res) status = 3; - sprintf((char *)buf, "%.64s@%.128s%c%hu", param->extusername, param->hostname, (ntohs(*SAPORT(¶m->sinsr))==21)?0:':', ntohs(*SAPORT(¶m->sinsr))); + sprintf((char *)buf, "%.128s@%.128s%c%hu", param->extusername, param->hostname, (ntohs(*SAPORT(¶m->sinsr))==21)?0:':', ntohs(*SAPORT(¶m->sinsr))); req = mystrdup((char *)buf); #ifndef WITHMAIN { diff --git a/src/pop3p.c b/src/pop3p.c index 46b4480..b5f3088 100644 --- a/src/pop3p.c +++ b/src/pop3p.c @@ -48,7 +48,7 @@ void * pop3pchild(struct clientparam* param) { CLEANRET: if(param->hostname&¶m->extusername) { - sprintf((char *)buf, "%.64s@%.128s%c%hu", param->extusername, param->hostname, (*SAPORT(¶m->sinsr)==110)?0:':', ntohs(*SAPORT(¶m->sinsr))); + sprintf((char *)buf, "%.128s@%.128s%c%hu", param->extusername, param->hostname, (*SAPORT(¶m->sinsr)==110)?0:':', ntohs(*SAPORT(¶m->sinsr))); (*param->srv->logfunc)(param, buf); } else (*param->srv->logfunc)(param, NULL); diff --git a/src/proxy.c b/src/proxy.c index 46bba1f..07eed13 100644 --- a/src/proxy.c +++ b/src/proxy.c @@ -131,8 +131,8 @@ char * proxy_stringtable[] = { NULL }; -#define BUFSIZE 8192 #define LINESIZE 4096 +#define BUFSIZE (LINESIZE*2) #define FTPBUFSIZE 1536 static void logurl(struct clientparam * param, char * buf, char * req, int ftp){ @@ -843,7 +843,7 @@ for(;;){ if(keepalive <= 1) sprintf((char*)buf+strlen((char *)buf), "%s: %s\r\n", (param->redirtype == R_HTTP)?"Proxy-Connection":"Connection", keepalive? "keep-alive":"close"); if(param->extusername){ sprintf((char*)buf + strlen((char *)buf), "%s: basic ", (redirect)?"Proxy-Authorization":"Authorization"); - sprintf((char*)username, "%.128s:%.64s", param->extusername, param->extpassword?param->extpassword:(unsigned char*)""); + sprintf((char*)username, "%.128s:%.128s", param->extusername, param->extpassword?param->extpassword:(unsigned char*)""); en64(username, buf+strlen((char *)buf), (int)strlen((char *)username)); sprintf((char*)buf + strlen((char *)buf), "\r\n"); } diff --git a/src/smtpp.c b/src/smtpp.c index 048f883..e40e4ea 100644 --- a/src/smtpp.c +++ b/src/smtpp.c @@ -291,7 +291,7 @@ void * smtppchild(struct clientparam* param) { CLEANRET: if(param->hostname&¶m->extusername) { - sprintf((char *)buf, "%.64s@%.128s%c%hu", param->extusername, param->hostname, *SAPORT(¶m->sinsr)==25?0:':',ntohs(*SAPORT(¶m->sinsr))); + sprintf((char *)buf, "%.128s@%.128s%c%hu", param->extusername, param->hostname, *SAPORT(¶m->sinsr)==25?0:':',ntohs(*SAPORT(¶m->sinsr))); (*param->srv->logfunc)(param, buf); } else (*param->srv->logfunc)(param, NULL); From eeb2d78fb1696b11fa944ef139e5c77b2cef6a03 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Mon, 28 Mar 2016 17:49:27 +0300 Subject: [PATCH 05/38] re-authenticate user on --- src/3proxy.c | 2 +- src/auth.c | 6 +++--- src/common.c | 2 +- src/conf.c | 1 + src/proxymain.c | 11 +++++++---- src/sockmap.c | 5 +++++ src/structures.h | 8 +++++--- 7 files changed, 23 insertions(+), 12 deletions(-) diff --git a/src/3proxy.c b/src/3proxy.c index 8675503..28006b9 100644 --- a/src/3proxy.c +++ b/src/3proxy.c @@ -59,8 +59,8 @@ void __stdcall CommandHandler( DWORD dwCommand ) case SERVICE_CONTROL_STOP: case SERVICE_CONTROL_SHUTDOWN: SetStatus( SERVICE_STOP_PENDING, 0, 1 ); - conf.paused++; conf.timetoexit = 1; + conf.paused++; Sleep(2000); SetStatus( SERVICE_STOPPED, 0, 0 ); #ifndef NOODBC diff --git a/src/auth.c b/src/auth.c index 83a7d82..3908bb3 100644 --- a/src/auth.c +++ b/src/auth.c @@ -476,8 +476,8 @@ unsigned bandlimitfunc(struct clientparam *param, unsigned nbytesin, unsigned nb if(!nbytesin && !nbytesout) return 0; pthread_mutex_lock(&bandlim_mutex); - if(param->srv->version != conf.paused){ - initbandlims(param); + if(param->paused != conf.paused){ + return (1); } for(i=0; nbytesin&& ibandlims[i]; i++){ if( !param->bandlims[i]->basetime || @@ -558,7 +558,7 @@ int alwaysauth(struct clientparam * param){ res = doconnect(param); if(!res){ - if(param->srv->version != conf.paused) return 333; + if(param->srv->paused != conf.paused) return 333; initbandlims(param); for(tc = conf.trafcounter; tc; tc = tc->next) { if(tc->disabled) continue; diff --git a/src/common.c b/src/common.c index d1b1439..b90175b 100644 --- a/src/common.c +++ b/src/common.c @@ -63,7 +63,7 @@ struct extparam conf = { #else 0, #endif - 0, -1, 0, 0, 0, 0, 0, 500, 0, 0, 0, + 0, -1, 0, 0, 0, 0, 0, 500, 0, 0, 0, 0, 6, 600, 1048576, NULL, NULL, diff --git a/src/conf.c b/src/conf.c index 0877803..88652b6 100644 --- a/src/conf.c +++ b/src/conf.c @@ -1685,6 +1685,7 @@ int reload (void){ fp = confopen(); if(fp){ + conf.version++; error = readconfig(fp); if(error) { freeconf(&conf); diff --git a/src/proxymain.c b/src/proxymain.c index d809b81..97b1b7d 100644 --- a/src/proxymain.c +++ b/src/proxymain.c @@ -509,7 +509,7 @@ int MODULEMAINFUNC (int argc, char** argv){ for (;;) { for(;;){ - while((conf.paused == srv.version && srv.childcount >= srv.maxchild)){ + while((conf.paused == srv.paused && srv.childcount >= srv.maxchild)){ nlog++; if(!srv.silent && nlog > 5000) { sprintf((char *)buf, "Warning: too many connected clients (%d/%d)", srv.childcount, srv.maxchild); @@ -519,7 +519,7 @@ int MODULEMAINFUNC (int argc, char** argv){ usleep(SLEEPTIME); } if (iscbc) break; - if (conf.paused != srv.version) break; + if (conf.paused != srv.paused) break; if (srv.fds.events & POLLIN) { error = so._poll(&srv.fds, 1, 1000); } @@ -535,7 +535,7 @@ int MODULEMAINFUNC (int argc, char** argv){ break; } } - if((conf.paused != srv.version) || (error < 0)) break; + if((conf.paused != srv.paused) || (error < 0)) break; error = 0; if(!isudp){ size = sizeof(defparam.sincr); @@ -710,7 +710,8 @@ int MODULEMAINFUNC (int argc, char** argv){ void srvinit(struct srvparam * srv, struct clientparam *param){ memset(srv, 0, sizeof(struct srvparam)); - srv->version = conf.paused; + srv->version = conf.version; + srv->paused = conf.paused; srv->logfunc = conf.logfunc; if(srv->logformat)myfree(srv->logformat); srv->logformat = conf.logformat? (unsigned char *)mystrdup((char *)conf.logformat) : NULL; @@ -730,6 +731,8 @@ void srvinit(struct srvparam * srv, struct clientparam *param){ srv->needuser = 1; memset(param, 0, sizeof(struct clientparam)); param->srv = srv; + param->version = srv->version; + param->paused = srv->paused; param->remsock = param->clisock = param->ctrlsock = param->ctrlsocksrv = INVALID_SOCKET; *SAFAMILY(¶m->req) = *SAFAMILY(¶m->sinsl) = *SAFAMILY(¶m->sinsr) = *SAFAMILY(¶m->sincr) = *SAFAMILY(¶m->sincl) = AF_INET; pthread_mutex_init(&srv->counter_mutex, NULL); diff --git a/src/sockmap.c b/src/sockmap.c index c3a9241..fd5b783 100644 --- a/src/sockmap.c +++ b/src/sockmap.c @@ -68,6 +68,11 @@ int sockmap(struct clientparam * param, int timeo){ while (!stop&&!conf.timetoexit){ sasize = sizeof(struct sockaddr_in); + if(param->version != conf.version){ + if (res = (*param->srv->authfunc)(param)) {return(res);} + param->paused = conf.paused; + param->version = conf.version; + } if((param->maxtrafin64 && param->statssrv64 >= param->maxtrafin64) || (param->maxtrafout64 && param->statscli64 >= param->maxtrafout64)){ return (10); } diff --git a/src/structures.h b/src/structures.h index b239eec..5008012 100644 --- a/src/structures.h +++ b/src/structures.h @@ -364,7 +364,7 @@ struct srvparam { SOCKET srvsock, cbsock; int childcount; int maxchild; - int version; + int paused, version; int singlepacket; int usentlm; int needuser; @@ -440,7 +440,9 @@ struct clientparam { nolongdatfilter, nooverwritefilter, transparent, - chunked; + chunked, + paused, + version; unsigned char *hostname, *username, @@ -494,7 +496,7 @@ struct extparam { struct trafcount * trafcounter; struct srvparam *services; int stacksize, threadinit, counterd, haveerror, rotate, paused, archiverc, - demon, maxchild, singlepacket, needreload, timetoexit; + demon, maxchild, singlepacket, needreload, timetoexit, version; int authcachetype, authcachetime; int filtermaxsize; unsigned char *logname, **archiver; From 938b1d1aabada1012826d1377a1caed751ef6c95 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Mon, 28 Mar 2016 17:57:37 +0300 Subject: [PATCH 06/38] re-authenticate connection on configuration change --- src/3proxy.c | 1 + src/conf.c | 2 +- src/proxymain.c | 2 +- src/sockmap.c | 2 +- 4 files changed, 4 insertions(+), 3 deletions(-) diff --git a/src/3proxy.c b/src/3proxy.c index 28006b9..7395b24 100644 --- a/src/3proxy.c +++ b/src/3proxy.c @@ -519,6 +519,7 @@ int WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int freeconf(&conf); res = readconfig(fp); + conf.version++; if(res) RETURN(res); if(!writable)fclose(fp); diff --git a/src/conf.c b/src/conf.c index 88652b6..8e23d32 100644 --- a/src/conf.c +++ b/src/conf.c @@ -1685,8 +1685,8 @@ int reload (void){ fp = confopen(); if(fp){ - conf.version++; error = readconfig(fp); + conf.version++; if(error) { freeconf(&conf); } diff --git a/src/proxymain.c b/src/proxymain.c index 97b1b7d..5340704 100644 --- a/src/proxymain.c +++ b/src/proxymain.c @@ -710,7 +710,7 @@ int MODULEMAINFUNC (int argc, char** argv){ void srvinit(struct srvparam * srv, struct clientparam *param){ memset(srv, 0, sizeof(struct srvparam)); - srv->version = conf.version; + srv->version = conf.version + 1; srv->paused = conf.paused; srv->logfunc = conf.logfunc; if(srv->logformat)myfree(srv->logformat); diff --git a/src/sockmap.c b/src/sockmap.c index fd5b783..40362f4 100644 --- a/src/sockmap.c +++ b/src/sockmap.c @@ -68,7 +68,7 @@ int sockmap(struct clientparam * param, int timeo){ while (!stop&&!conf.timetoexit){ sasize = sizeof(struct sockaddr_in); - if(param->version != conf.version){ + if(param->version < conf.version){ if (res = (*param->srv->authfunc)(param)) {return(res);} param->paused = conf.paused; param->version = conf.version; From 6cac541e33c8ff441135372e00d193219847fc0f Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 30 Mar 2016 19:16:12 +0300 Subject: [PATCH 07/38] fix broken extip functionality --- src/common.c | 8 +++++--- src/proxy.c | 8 +++++++- 2 files changed, 12 insertions(+), 4 deletions(-) diff --git a/src/common.c b/src/common.c index b90175b..3a8b26e 100644 --- a/src/common.c +++ b/src/common.c @@ -669,11 +669,13 @@ int doconnect(struct clientparam * param){ } #endif + if(SAISNULL(¶m->sinsl)){ #ifndef NOIPV6 - if(*SAFAMILY(¶m->sinsr) == AF_INET6) param->sinsl = param->srv->extsa6; - else + if(*SAFAMILY(¶m->sinsr) == AF_INET6) param->sinsl = param->srv->extsa6; + else #endif - param->sinsl = param->srv->extsa; + param->sinsl = param->srv->extsa; + } *SAPORT(¶m->sinsl) = 0; if(so._bind(param->remsock, (struct sockaddr*)¶m->sinsl, SASIZE(¶m->sinsl))==-1) { return 12; diff --git a/src/proxy.c b/src/proxy.c index 07eed13..8ac62c4 100644 --- a/src/proxy.c +++ b/src/proxy.c @@ -152,7 +152,7 @@ static void logurl(struct clientparam * param, char * buf, char * req, int ftp){ strcpy(se, sb); } } - if(param->res != 555)(*param->srv->logfunc)(param, (unsigned char *)(req?buf:NULL)); + if(param->res != 555 && param->res != 508)(*param->srv->logfunc)(param, (unsigned char *)(req?buf:NULL)); } void decodeurl(unsigned char *s, int allowcr){ @@ -264,6 +264,9 @@ for(;;){ param->remsock = INVALID_SOCKET; param->redirected = 0; param->redirtype = 0; + memset(¶m->sinsl, 0, sizeof(param->sinsl)); + memset(¶m->sinsr, 0, sizeof(param->sinsr)); + memset(¶m->req, 0, sizeof(param->req)); } } @@ -284,6 +287,9 @@ for(;;){ param->remsock = INVALID_SOCKET; param->redirected = 0; param->redirtype = 0; + memset(¶m->sinsl, 0, sizeof(param->sinsl)); + memset(¶m->sinsr, 0, sizeof(param->sinsr)); + memset(¶m->req, 0, sizeof(param->req)); } myfree(req); } From 2fed299b9d124eaa215c20da6df097dd0c7b78b6 Mon Sep 17 00:00:00 2001 From: Vladimir Dubrovin <3proxy@3proxy.ru> Date: Sat, 2 Apr 2016 11:22:33 +0300 Subject: [PATCH 08/38] warning fix --- src/sockmap.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/sockmap.c b/src/sockmap.c index 40362f4..04d30b3 100644 --- a/src/sockmap.c +++ b/src/sockmap.c @@ -69,7 +69,7 @@ int sockmap(struct clientparam * param, int timeo){ while (!stop&&!conf.timetoexit){ sasize = sizeof(struct sockaddr_in); if(param->version < conf.version){ - if (res = (*param->srv->authfunc)(param)) {return(res);} + if ((res = (*param->srv->authfunc)(param))) {return(res);} param->paused = conf.paused; param->version = conf.version; } From 9bfae5faaa39777bf0eaab434ba9ec65b5684817 Mon Sep 17 00:00:00 2001 From: Vladimir Dubrovin <3proxy@3proxy.ru> Date: Sat, 2 Apr 2016 11:43:25 +0300 Subject: [PATCH 09/38] force / no force commands added --- src/common.c | 2 +- src/conf.c | 13 +++++++++++++ src/proxymain.c | 1 + src/structures.h | 3 ++- 4 files changed, 17 insertions(+), 2 deletions(-) diff --git a/src/common.c b/src/common.c index 3a8b26e..8c0ba6c 100644 --- a/src/common.c +++ b/src/common.c @@ -63,7 +63,7 @@ struct extparam conf = { #else 0, #endif - 0, -1, 0, 0, 0, 0, 0, 500, 0, 0, 0, 0, + 0, -1, 0, 0, 0, 0, 0, 500, 0, 0, 0, 0, 0, 6, 600, 1048576, NULL, NULL, diff --git a/src/conf.c b/src/conf.c index 8e23d32..16c377e 100644 --- a/src/conf.c +++ b/src/conf.c @@ -340,6 +340,17 @@ static int h_stacksize(int argc, unsigned char **argv){ return 0; } + +static int h_force(int argc, unsigned char **argv){ + conf.noforce = 0; + return 0; +} + +static int h_noforce(int argc, unsigned char **argv){ + conf.noforce = 1; + return 0; +} + static int h_service(int argc, unsigned char **argv){ return 0; } @@ -1399,6 +1410,8 @@ struct commands commandhandlers[]={ {commandhandlers+56, "delimchar",h_delimchar, 2, 2}, {commandhandlers+57, "authnserver", h_authnserver, 2, 2}, {commandhandlers+58, "stacksize", h_stacksize, 2, 2}, + {commandhandlers+59, "force", h_force, 1, 1}, + {commandhandlers+60, "noforce", h_noforce, 1, 1}, {specificcommands, "", h_noop, 1, 0} }; diff --git a/src/proxymain.c b/src/proxymain.c index 5340704..d6c1a37 100644 --- a/src/proxymain.c +++ b/src/proxymain.c @@ -713,6 +713,7 @@ void srvinit(struct srvparam * srv, struct clientparam *param){ srv->version = conf.version + 1; srv->paused = conf.paused; srv->logfunc = conf.logfunc; + srv->noforce = conf.noforce; if(srv->logformat)myfree(srv->logformat); srv->logformat = conf.logformat? (unsigned char *)mystrdup((char *)conf.logformat) : NULL; srv->authfunc = conf.authfunc; diff --git a/src/structures.h b/src/structures.h index 5008012..9f286be 100644 --- a/src/structures.h +++ b/src/structures.h @@ -373,6 +373,7 @@ struct srvparam { int nfilters, nreqfilters, nhdrfilterscli, nhdrfilterssrv, npredatfilters, ndatfilterscli, ndatfilterssrv; int family; int stacksize; + int noforce; unsigned bufsize; unsigned logdumpsrv, logdumpcli; #ifndef NOIPV6 @@ -496,7 +497,7 @@ struct extparam { struct trafcount * trafcounter; struct srvparam *services; int stacksize, threadinit, counterd, haveerror, rotate, paused, archiverc, - demon, maxchild, singlepacket, needreload, timetoexit, version; + demon, maxchild, singlepacket, needreload, timetoexit, version, noforce; int authcachetype, authcachetime; int filtermaxsize; unsigned char *logname, **archiver; From e210f24194809763d35100a7e7f143dfe2a87080 Mon Sep 17 00:00:00 2001 From: Vladimir Dubrovin <3proxy@3proxy.ru> Date: Sat, 2 Apr 2016 12:00:53 +0300 Subject: [PATCH 10/38] fix for noforce --- src/sockmap.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/sockmap.c b/src/sockmap.c index 04d30b3..d3ccdf6 100644 --- a/src/sockmap.c +++ b/src/sockmap.c @@ -69,7 +69,7 @@ int sockmap(struct clientparam * param, int timeo){ while (!stop&&!conf.timetoexit){ sasize = sizeof(struct sockaddr_in); if(param->version < conf.version){ - if ((res = (*param->srv->authfunc)(param))) {return(res);} + if((res = (*param->srv->authfunc)(param)) && !param->srv->noforce) {return(res);} param->paused = conf.paused; param->version = conf.version; } From d6f72a51fe46b55758d63ca6bc09bbc5bf6199fc Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Mon, 4 Apr 2016 13:43:08 +0300 Subject: [PATCH 11/38] fix race condition on 'log' command processing --- src/conf.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/conf.c b/src/conf.c index 8e23d32..6730011 100644 --- a/src/conf.c +++ b/src/conf.c @@ -314,22 +314,23 @@ static int h_log(int argc, unsigned char ** argv){ } conf.logtime = time(0); if(conf.logname)myfree(conf.logname); + pthread_mutex_lock(&log_mutex); conf.logname = (unsigned char *)mystrdup((char *)argv[1]); fp = fopen((char *)dologname (tmpbuf, conf.logname, NULL, conf.logtype, conf.logtime), "a"); if(!fp){ - perror("fopen()"); + perror(tmpbuf); + pthread_mutex_unlock(&log_mutex); return 1; } else { - pthread_mutex_lock(&log_mutex); if(conf.stdlog)fclose(conf.stdlog); conf.stdlog = fp; - pthread_mutex_unlock(&log_mutex); #ifdef _WINCE freopen(tmpbuf, "w", stdout); freopen(tmpbuf, "w", stderr); #endif } + pthread_mutex_unlock(&log_mutex); } } return 0; From d3f9d80b6571dd50c56074824a3477e1bc1a16a2 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 5 Apr 2016 19:12:18 +0300 Subject: [PATCH 12/38] Resolve races on log buffer without mutex --- src/3proxy.c | 3 +++ src/conf.c | 4 +--- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/src/3proxy.c b/src/3proxy.c index 7395b24..09cf607 100644 --- a/src/3proxy.c +++ b/src/3proxy.c @@ -192,6 +192,7 @@ void doschedule(void){ void dumpcounters(struct trafcount *tlin, int counterd){ + unsigned char tmpbuf[8192]; struct trafcount *tl; if(counterd >= 0 && tlin) { @@ -234,6 +235,7 @@ void dumpcounters(struct trafcount *tlin, int counterd){ void cyclestep(void){ struct tm *tm; time_t minutecounter; + unsigned char tmpbuf[8192]; minutecounter = time(0); for(;;){ @@ -362,6 +364,7 @@ int WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int #ifdef _WIN32 unsigned char * arg; WSADATA wd; + unsigned char tmpbuf[8192]; WSAStartup(MAKEWORD( 1, 1 ), &wd); osv.dwOSVersionInfoSize = sizeof(osv); diff --git a/src/conf.c b/src/conf.c index 1d9ae9d..a9fa228 100644 --- a/src/conf.c +++ b/src/conf.c @@ -285,6 +285,7 @@ static int h_external(int argc, unsigned char ** argv){ } static int h_log(int argc, unsigned char ** argv){ + unsigned char tmpbuf[8192]; conf.logfunc = logstdout; if(conf.logtarget){ myfree(conf.logtarget); @@ -314,12 +315,10 @@ static int h_log(int argc, unsigned char ** argv){ } conf.logtime = time(0); if(conf.logname)myfree(conf.logname); - pthread_mutex_lock(&log_mutex); conf.logname = (unsigned char *)mystrdup((char *)argv[1]); fp = fopen((char *)dologname (tmpbuf, conf.logname, NULL, conf.logtype, conf.logtime), "a"); if(!fp){ perror(tmpbuf); - pthread_mutex_unlock(&log_mutex); return 1; } else { @@ -330,7 +329,6 @@ static int h_log(int argc, unsigned char ** argv){ freopen(tmpbuf, "w", stderr); #endif } - pthread_mutex_unlock(&log_mutex); } } return 0; From 3c8c866ac14a3f146622c79ddad2b009eb16acdf Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Fri, 8 Apr 2016 14:53:15 +0300 Subject: [PATCH 13/38] Fix counters time check for different platforms --- src/conf.c | 21 ++++++++++++--------- 1 file changed, 12 insertions(+), 9 deletions(-) diff --git a/src/conf.c b/src/conf.c index a9fa228..c174781 100644 --- a/src/conf.c +++ b/src/conf.c @@ -405,17 +405,22 @@ static int h_counter(int argc, unsigned char **argv){ fprintf(stderr, "Not a counter file %s, line %d\n", argv[1], linenum); return 2; } -#ifdef _MSC_VER #ifdef _TIME64_T_DEFINED -#ifndef _MAX__TIME64_T -#define _MAX__TIME64_T 0x793406fffi64 +#ifdef _MAX__TIME64_T +#define MAX_COUNTER_TIME (_MAX__TIME64_T) +#elif defined (MAX__TIME64_T) +#define MAX_COUNTER_TIME (MAX__TIME64_T) +#else +#define MAX_COUNTER_TIME (0x793406fff) #endif +#else +#define MAX_COUNTER_TIME ((sizeof(time_t)>4)?0x793406fff:LONG_MAX) #endif - if(ch1.updated >= _MAX__TIME64_T){ + + if(ch1.updated < 0 || ch1.updated >= MAX_COUNTER_TIME){ fprintf(stderr, "Invalid or corrupted counter file %s. Use countersutil utility to convert from older version\n", argv[1]); return 3; } -#endif cheader.updated = ch1.updated; } if(argc >=4) { @@ -1209,12 +1214,10 @@ static int h_ace(int argc, unsigned char **argv){ tl->traf64 = crecord.traf64; tl->cleared = crecord.cleared; tl->updated = crecord.updated; -#ifdef _MAX__TIME64_T - if(tl->cleared >= _MAX__TIME64_T || tl->updated >= _MAX__TIME64_T){ - fprintf(stderr, "Invalid or corrupted counter file. Use countersutil utility to convert from older version\n"); + if(tl->cleared < 0 || tl->cleared >= MAX_COUNTER_TIME || tl->updated < 0 || tl->updated >= MAX_COUNTER_TIME){ + fprintf(stderr, "Invalid, incompatible or corrupted counter file.\n"); return(6); } -#endif } } pthread_mutex_lock(&tc_mutex); From 8b1c12005f3c2aaa36fa84818df120a2859d705e Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Fri, 8 Apr 2016 15:08:18 +0300 Subject: [PATCH 14/38] avoid type mismatch in ?: operator --- src/conf.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/conf.c b/src/conf.c index c174781..632acf8 100644 --- a/src/conf.c +++ b/src/conf.c @@ -414,7 +414,7 @@ static int h_counter(int argc, unsigned char **argv){ #define MAX_COUNTER_TIME (0x793406fff) #endif #else -#define MAX_COUNTER_TIME ((sizeof(time_t)>4)?0x793406fff:LONG_MAX) +#define MAX_COUNTER_TIME ((sizeof(time_t)>4)?(time_t)0x793406fff:(time_t)0x7fffffff) #endif if(ch1.updated < 0 || ch1.updated >= MAX_COUNTER_TIME){ From cfa4d1102760918ec76191aae563c52e3122e018 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 26 Apr 2016 18:50:57 +0300 Subject: [PATCH 15/38] Do not fail connection with 333 error on configuration reload --- src/auth.c | 1 - src/sockmap.c | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/auth.c b/src/auth.c index 3908bb3..2c89c65 100644 --- a/src/auth.c +++ b/src/auth.c @@ -558,7 +558,6 @@ int alwaysauth(struct clientparam * param){ res = doconnect(param); if(!res){ - if(param->srv->paused != conf.paused) return 333; initbandlims(param); for(tc = conf.trafcounter; tc; tc = tc->next) { if(tc->disabled) continue; diff --git a/src/sockmap.c b/src/sockmap.c index d3ccdf6..a2cd9b2 100644 --- a/src/sockmap.c +++ b/src/sockmap.c @@ -69,7 +69,7 @@ int sockmap(struct clientparam * param, int timeo){ while (!stop&&!conf.timetoexit){ sasize = sizeof(struct sockaddr_in); if(param->version < conf.version){ - if((res = (*param->srv->authfunc)(param)) && !param->srv->noforce) {return(res);} + if((res = (*param->srv->authfunc)(param)) && res != 2 && !param->srv->noforce) {return(res);} param->paused = conf.paused; param->version = conf.version; } From 8e820b28c06a147d3b66fa9cd3e3c77796b6a370 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 11 May 2016 19:02:51 +0300 Subject: [PATCH 16/38] Documentation correction --- doc/html/faqr.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/html/faqr.html b/doc/html/faqr.html index cd4cfec..9b888e6 100644 --- a/doc/html/faqr.html +++ b/doc/html/faqr.html @@ -129,7 +129,7 @@ невозможен. Защитить соединение можно с помощью TLS (например, stunnel) или IPSec.

-
  • Q: Почему прокси крэшится при обработке запроса?
  • +
  • Q: Почему прокси крэшится при обработке запроса?
  • A: Возможно, недостаточен размер стека потока по-умолчанию, это может быть при использовани каких-либо сторонних плагинов (PAM, ODBC) или на From 4cb43b438fd5bd6006d30c280ca11b7fa532b9a6 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 11 May 2016 19:03:16 +0300 Subject: [PATCH 17/38] Use mutex with pam auth, because pam is not thread safe --- src/plugins/PamAuth/pamauth.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/plugins/PamAuth/pamauth.c b/src/plugins/PamAuth/pamauth.c index 4e182c6..da8869d 100644 --- a/src/plugins/PamAuth/pamauth.c +++ b/src/plugins/PamAuth/pamauth.c @@ -12,7 +12,7 @@ Kirill Lopuchov #include - +pthread_mutex_t pam_mutex; static int already_loaded = 0; @@ -89,9 +89,10 @@ static int pamfunc(struct clientparam *param) /*start process auth */ conv.appdata_ptr = (char *) param->password; + pthread_mutex_lock(&pam_mutex); if (!pamh) { - retval = pam_start ((char *)service, "3proxy@" , &conv, &pamh); + retval = pam_start ((char *)service, "3proxy@" , &conv, &pamh); } if (retval == PAM_SUCCESS) retval = pam_set_item (pamh, PAM_USER, param->username); @@ -110,6 +111,7 @@ static int pamfunc(struct clientparam *param) retval = pam_end (pamh, retval); if (retval != PAM_SUCCESS) { pamh = NULL; } + pthread_mutex_unlock(&pam_mutex); return rc; @@ -130,6 +132,7 @@ int start(struct pluginlink * pluginlink, int argc, unsigned char** argv) already_loaded = 1; + pthread_mutex_init(&pam_mutex, NULL); pamauth.authenticate = pamfunc; pamauth.authorize = pluginlink->checkACL; pamauth.desc = "pam"; From 438a5bac9b53e2412a698316c172cc8655711abd Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 11 May 2016 19:56:40 +0300 Subject: [PATCH 18/38] pam_auth: Authenticate all users in single session --- src/plugins/PamAuth/pamauth.c | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-) diff --git a/src/plugins/PamAuth/pamauth.c b/src/plugins/PamAuth/pamauth.c index da8869d..2fe5140 100644 --- a/src/plugins/PamAuth/pamauth.c +++ b/src/plugins/PamAuth/pamauth.c @@ -13,6 +13,7 @@ Kirill Lopuchov pthread_mutex_t pam_mutex; +pam_handle_t *pamh = NULL; static int already_loaded = 0; @@ -69,7 +70,6 @@ static void lower (char *string) /* --------------------------------------------------------------------------*/ static int pamfunc(struct clientparam *param) { - pam_handle_t *pamh = NULL; int retval; int rc=0; @@ -90,10 +90,8 @@ static int pamfunc(struct clientparam *param) conv.appdata_ptr = (char *) param->password; pthread_mutex_lock(&pam_mutex); - if (!pamh) - { + if (!pamh) retval = pam_start ((char *)service, "3proxy@" , &conv, &pamh); - } if (retval == PAM_SUCCESS) retval = pam_set_item (pamh, PAM_USER, param->username); /*fprintf(stderr,"pam_set_item1 rc=%d\n",retval);*/ @@ -104,15 +102,11 @@ static int pamfunc(struct clientparam *param) retval = pam_authenticate (pamh, 0); /*fprintf(stderr,"pam_authenticate rc=%d\n",retval);*/ + pthread_mutex_unlock(&pam_mutex); + if (retval == PAM_SUCCESS) { /*auth OK*/ rc=0; } else { /*auth ERR*/ rc=5; } - if (pamh) - retval = pam_end (pamh, retval); - if (retval != PAM_SUCCESS) - { pamh = NULL; } - pthread_mutex_unlock(&pam_mutex); - return rc; } From 32ff1147877418fa1940dd79f3545869fbdf96ac Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 11 May 2016 20:49:39 +0300 Subject: [PATCH 19/38] Revert "pam_auth: Authenticate all users in single session" This reverts commit 438a5bac9b53e2412a698316c172cc8655711abd. --- src/plugins/PamAuth/pamauth.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/src/plugins/PamAuth/pamauth.c b/src/plugins/PamAuth/pamauth.c index 2fe5140..da8869d 100644 --- a/src/plugins/PamAuth/pamauth.c +++ b/src/plugins/PamAuth/pamauth.c @@ -13,7 +13,6 @@ Kirill Lopuchov pthread_mutex_t pam_mutex; -pam_handle_t *pamh = NULL; static int already_loaded = 0; @@ -70,6 +69,7 @@ static void lower (char *string) /* --------------------------------------------------------------------------*/ static int pamfunc(struct clientparam *param) { + pam_handle_t *pamh = NULL; int retval; int rc=0; @@ -90,8 +90,10 @@ static int pamfunc(struct clientparam *param) conv.appdata_ptr = (char *) param->password; pthread_mutex_lock(&pam_mutex); - if (!pamh) + if (!pamh) + { retval = pam_start ((char *)service, "3proxy@" , &conv, &pamh); + } if (retval == PAM_SUCCESS) retval = pam_set_item (pamh, PAM_USER, param->username); /*fprintf(stderr,"pam_set_item1 rc=%d\n",retval);*/ @@ -102,11 +104,15 @@ static int pamfunc(struct clientparam *param) retval = pam_authenticate (pamh, 0); /*fprintf(stderr,"pam_authenticate rc=%d\n",retval);*/ - pthread_mutex_unlock(&pam_mutex); - if (retval == PAM_SUCCESS) { /*auth OK*/ rc=0; } else { /*auth ERR*/ rc=5; } + if (pamh) + retval = pam_end (pamh, retval); + if (retval != PAM_SUCCESS) + { pamh = NULL; } + pthread_mutex_unlock(&pam_mutex); + return rc; } From 556fea670eef3e1e42bbcab04fa9c8b81f971fb3 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 11 May 2016 20:51:14 +0300 Subject: [PATCH 20/38] pam_auth; lock only pam_start --- src/plugins/PamAuth/pamauth.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/plugins/PamAuth/pamauth.c b/src/plugins/PamAuth/pamauth.c index da8869d..1e2250a 100644 --- a/src/plugins/PamAuth/pamauth.c +++ b/src/plugins/PamAuth/pamauth.c @@ -94,6 +94,7 @@ static int pamfunc(struct clientparam *param) { retval = pam_start ((char *)service, "3proxy@" , &conv, &pamh); } + pthread_mutex_unlock(&pam_mutex); if (retval == PAM_SUCCESS) retval = pam_set_item (pamh, PAM_USER, param->username); /*fprintf(stderr,"pam_set_item1 rc=%d\n",retval);*/ @@ -111,7 +112,6 @@ static int pamfunc(struct clientparam *param) retval = pam_end (pamh, retval); if (retval != PAM_SUCCESS) { pamh = NULL; } - pthread_mutex_unlock(&pam_mutex); return rc; From ccbc94e06bd818dd10eeb5edc5dbe1d8377e3c1b Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 11 May 2016 22:05:45 +0300 Subject: [PATCH 21/38] Revert "pam_auth; lock only pam_start" This reverts commit 556fea670eef3e1e42bbcab04fa9c8b81f971fb3. --- src/plugins/PamAuth/pamauth.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/plugins/PamAuth/pamauth.c b/src/plugins/PamAuth/pamauth.c index 1e2250a..da8869d 100644 --- a/src/plugins/PamAuth/pamauth.c +++ b/src/plugins/PamAuth/pamauth.c @@ -94,7 +94,6 @@ static int pamfunc(struct clientparam *param) { retval = pam_start ((char *)service, "3proxy@" , &conv, &pamh); } - pthread_mutex_unlock(&pam_mutex); if (retval == PAM_SUCCESS) retval = pam_set_item (pamh, PAM_USER, param->username); /*fprintf(stderr,"pam_set_item1 rc=%d\n",retval);*/ @@ -112,6 +111,7 @@ static int pamfunc(struct clientparam *param) retval = pam_end (pamh, retval); if (retval != PAM_SUCCESS) { pamh = NULL; } + pthread_mutex_unlock(&pam_mutex); return rc; From 8cdf341d0e7f03a6c7b520962d935cdd75ab9c1d Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Sat, 14 May 2016 00:09:51 +0300 Subject: [PATCH 22/38] workaround for broken getsockname() in FTP proxy --- src/common.c | 2 +- src/ftp.c | 17 +++++++++++++++-- 2 files changed, 16 insertions(+), 3 deletions(-) diff --git a/src/common.c b/src/common.c index 8c0ba6c..9e3cb25 100644 --- a/src/common.c +++ b/src/common.c @@ -694,8 +694,8 @@ int doconnect(struct clientparam * param){ #else fcntl(param->remsock,F_SETFL,O_NONBLOCK); #endif - size = sizeof(param->sinsl); } + size = sizeof(param->sinsl); if(so._getsockname(param->remsock, (struct sockaddr *)¶m->sinsl, &size)==-1) {return (15);} } return 0; diff --git a/src/ftp.c b/src/ftp.c index 3007ade..2480aa9 100644 --- a/src/ftp.c +++ b/src/ftp.c @@ -174,6 +174,7 @@ SOCKET ftpdata(struct clientparam *param){ SOCKET s = INVALID_SOCKET, rem; unsigned long b1, b2, b3, b4; unsigned short b5, b6; + SASIZETYPE sasize; if(socksend(param->remsock, (unsigned char *)"PASV\r\n", 6, conf.timeouts[STRING_S]) != 6){ return INVALID_SOCKET; @@ -187,15 +188,27 @@ SOCKET ftpdata(struct clientparam *param){ buf[i-2] = 0; if(!(sb = strchr(buf+4, '(')) || !(se= strchr(sb, ')'))) return INVALID_SOCKET; if(sscanf(sb+1, "%lu,%lu,%lu,%lu,%hu,%hu", &b1, &b2, &b3, &b4, &b5, &b6)!=6) return INVALID_SOCKET; + sasize = sizeof(param->sinsl); + if(so._getsockname(param->remsock, (struct sockaddr *)¶m->sinsl, &sasize)){return INVALID_SOCKET;} + sasize = sizeof(param->sinsr); + if(so._getpeername(param->remsock, (struct sockaddr *)¶m->sinsr, &sasize)){return INVALID_SOCKET;} rem = param->remsock; param->remsock = INVALID_SOCKET; param->req = param->sinsr; *SAPORT(¶m->req) = *SAPORT(¶m->sinsr) = htons((unsigned short)((b5<<8)^b6)); + *SAPORT(¶m->sinsl) = 0; i = param->operation; param->operation = FTP_DATA; if((param->res = (*param->srv->authfunc)(param))) { - param->remsock = rem; - return INVALID_SOCKET; + if(param->remsock != INVALID_SOCKET) { + so._closesocket(param->remsock); + param->remsock = INVALID_SOCKET; + } + memset(¶m->sinsl, 0, sizeof(param->sinsl)); + if((param->res = (*param->srv->authfunc)(param))) { + param->remsock = rem; + return INVALID_SOCKET; + } } param->operation = i; s = param->remsock; From fbcdcf3d7b663efa659cb9ef3b34ea7e783e0314 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 17 May 2016 23:27:10 +0300 Subject: [PATCH 23/38] Correct IP matching in cache auth --- src/auth.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/auth.c b/src/auth.c index 2c89c65..874bc34 100644 --- a/src/auth.c +++ b/src/auth.c @@ -654,7 +654,7 @@ int cacheauth(struct clientparam * param){ } if(((!(conf.authcachetype&2)) || (param->username && ac->username && !strcmp(ac->username, (char *)param->username))) && - ((!(conf.authcachetype&1)) || (*SAFAMILY(&ac->sa) == *SAFAMILY(¶m->sincr) && !memcmp(SAADDR(&ac->sa), ¶m->sincr, SAADDRLEN(&ac->sa)))) && + ((!(conf.authcachetype&1)) || (*SAFAMILY(&ac->sa) == *SAFAMILY(¶m->sincr) && !memcmp(SAADDR(&ac->sa), SAADDR(¶m->sincr), SAADDRLEN(&ac->sa)))) && (!(conf.authcachetype&4) || (ac->password && param->password && !strcmp(ac->password, (char *)param->password)))) { if(param->username){ myfree(param->username); @@ -688,7 +688,7 @@ int doauth(struct clientparam * param){ pthread_mutex_lock(&hash_mutex); for(ac = authc; ac; ac = ac->next){ if((!(conf.authcachetype&2) || !strcmp(ac->username, (char *)param->username)) && - (!(conf.authcachetype&1) || (*SAFAMILY(&ac->sa) == *SAFAMILY(¶m->sincr) && !memcmp(SAADDR(&ac->sa), ¶m->sincr, SAADDRLEN(&ac->sa)))) && + (!(conf.authcachetype&1) || (*SAFAMILY(&ac->sa) == *SAFAMILY(¶m->sincr) && !memcmp(SAADDR(&ac->sa), SAADDR(¶m->sincr), SAADDRLEN(&ac->sa)))) && (!(conf.authcachetype&4) || (ac->password && !strcmp(ac->password, (char *)param->password)))) { ac->expires = conf.time + conf.authcachetime; if(strcmp(ac->username, (char *)param->username)){ @@ -709,7 +709,7 @@ int doauth(struct clientparam * param){ ac = myalloc(sizeof(struct authcache)); if(ac){ ac->expires = conf.time + conf.authcachetime; - ac->username = mystrdup((char *)param->username); + ac->username = param->username?mystrdup((char *)param->username):NULL; ac->sa = param->sincr; ac->password = NULL; if((conf.authcachetype&4) && param->password) ac->password = mystrdup((char *)param->password); From f347b37770c40227ee1a8d743f7dab9656bdb005 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Wed, 18 May 2016 00:05:23 +0300 Subject: [PATCH 24/38] support port number in 'nserver' / 'authnserver' --- src/common.c | 22 +++++++++++++--------- src/conf.c | 4 ++-- src/proxy.h | 2 +- 3 files changed, 16 insertions(+), 12 deletions(-) diff --git a/src/common.c b/src/common.c index 9e3cb25..9550393 100644 --- a/src/common.c +++ b/src/common.c @@ -221,30 +221,34 @@ int ceparseargs(const char *str){ #endif -void parsehost(int family, unsigned char *host, struct sockaddr *sa){ +int parsehost(int family, unsigned char *host, struct sockaddr *sa){ char *sp=NULL,*se=NULL; - unsigned short port; + unsigned short port=0; + int ret = 0; + if(!host) return 2; if(*host == '[') se=strchr((char *)host, ']'); - if ( (sp = strchr(se?se:(char *)host, ':')) ) *sp = 0; + if ( (sp = strchr(se?se:(char *)host, ':')) && !strchr(sp+1, ':')) *sp = 0; if(se){ *se = 0; } if(sp){ port = atoi(sp+1); } - getip46(family, host + (se!=0), (struct sockaddr *)sa); + ret = !getip46(family, host + (se!=0), (struct sockaddr *)sa); if(se) *se = ']'; if(sp) *sp = ':'; - *SAPORT(sa) = htons(port); + if(port)*SAPORT(sa) = htons(port); + return ret; } int parsehostname(char *hostname, struct clientparam *param, unsigned short port){ char *sp=NULL,*se=NULL; + int ret = 0; - if(!hostname || !*hostname)return 1; + if(!hostname || !*hostname)return 2; if(*hostname == '[') se=strchr(hostname, ']'); - if ( (sp = strchr(se?se:hostname, ':')) ) *sp = 0; + if ( (sp = strchr(se?se:hostname, ':')) && !strchr(sp+1, ':')) *sp = 0; if(se){ *se = 0; } @@ -255,12 +259,12 @@ int parsehostname(char *hostname, struct clientparam *param, unsigned short port if(sp){ port = atoi(sp+1); } - getip46(param->srv->family, param->hostname, (struct sockaddr *)¶m->req); + ret = !getip46(param->srv->family, param->hostname, (struct sockaddr *)¶m->req); if(se) *se = ']'; if(sp) *sp = ':'; *SAPORT(¶m->req) = htons(port); memset(¶m->sinsr, 0, sizeof(param->sinsr)); - return 0; + return ret; } int parseusername(char *username, struct clientparam *param, int extpasswd){ diff --git a/src/conf.c b/src/conf.c index 632acf8..735a222 100644 --- a/src/conf.c +++ b/src/conf.c @@ -563,8 +563,8 @@ static int h_nserver(int argc, unsigned char **argv){ if(numservers < MAXNSERVERS) { if((str = strchr((char *)argv[1], '/'))) *str = 0; - if(!getip46(46, argv[1], (struct sockaddr *)&nservers[numservers].addr)) return 1; *SAPORT(&nservers[numservers].addr) = htons(53); + if(parsehost(46, argv[1], (struct sockaddr *)&nservers[numservers].addr)) return 1; if(str) { nservers[numservers].usetcp = strstr(str + 1, "tcp")? 1:0; *str = '/'; @@ -581,7 +581,7 @@ static int h_authnserver(int argc, unsigned char **argv){ if((str = strchr((char *)argv[1], '/'))) *str = 0; - if(!getip46(46, argv[1], (struct sockaddr *)&authnserver.addr)) return 1; + if(parsehost(46, argv[1], (struct sockaddr *)&authnserver.addr)) return 1; *SAPORT(&authnserver.addr) = htons(53); if(str) { authnserver.usetcp = strstr(str + 1, "tcp")? 1:0; diff --git a/src/proxy.h b/src/proxy.h index 3c93658..061cfff 100644 --- a/src/proxy.h +++ b/src/proxy.h @@ -233,7 +233,7 @@ void mschap(const unsigned char *win_password, struct hashtable; void hashadd(struct hashtable *ht, const unsigned char* name, unsigned char* value, time_t expires); -void parsehost(int family, unsigned char *host, struct sockaddr *sa); +int parsehost(int family, unsigned char *host, struct sockaddr *sa); int parsehostname(char *hostname, struct clientparam *param, unsigned short port); int parseusername(char *username, struct clientparam *param, int extpasswd); int parseconnusername(char *username, struct clientparam *param, int extpasswd, unsigned short port); From cd3521553276340771bfd83c6afdd1aa4d1d2c92 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Sat, 28 May 2016 00:24:26 +0300 Subject: [PATCH 25/38] support -u2 for proxy --- src/proxy.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/proxy.c b/src/proxy.c index 8ac62c4..b05075e 100644 --- a/src/proxy.c +++ b/src/proxy.c @@ -552,6 +552,7 @@ for(;;){ #endif + if(param->srv->needuser > 1 && !param->username) {RETURN(4);} if((res = (*param->srv->authfunc)(param))) {RETURN(res);} if(ftp && param->redirtype != R_HTTP){ From 84664a203b6da096e53cdd8d230fd92ee6c87acd Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Mon, 6 Jun 2016 17:54:23 +0300 Subject: [PATCH 26/38] support %i in loformat --- man/3proxy.cfg.3 | 2 ++ src/common.c | 3 +++ 2 files changed, 5 insertions(+) diff --git a/man/3proxy.cfg.3 b/man/3proxy.cfg.3 index ac87e42..22f141c 100644 --- a/man/3proxy.cfg.3 +++ b/man/3proxy.cfg.3 @@ -300,6 +300,8 @@ with space and all time based elemnts are in local time zone. %R - Remote IP .br %r - Remote port +.br + %i - Internal IP used to accept client connection .br %e - External IP used to establish connection .br diff --git a/src/common.c b/src/common.c index 9550393..854f5b2 100644 --- a/src/common.c +++ b/src/common.c @@ -502,6 +502,9 @@ int dobuf2(struct clientparam * param, unsigned char * buf, const unsigned char case 'e': i += myinet_ntop(*SAFAMILY(¶m->sinsl), SAADDR(¶m->sinsl), (char *)buf + i, 64); break; + case 'i': + i += myinet_ntop(*SAFAMILY(¶m->sincl), SAADDR(¶m->sinsl), (char *)buf + i, 64); + break; case 'C': i += myinet_ntop(*SAFAMILY(¶m->sincr), SAADDR(¶m->sincr), (char *)buf + i, 64); break; From 05f39246bfd3599673d9e863c889861911065d61 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Mon, 6 Jun 2016 18:01:51 +0300 Subject: [PATCH 27/38] Delay service exit until new configuration is loaded --- src/proxymain.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/proxymain.c b/src/proxymain.c index d6c1a37..4aea520 100644 --- a/src/proxymain.c +++ b/src/proxymain.c @@ -685,7 +685,7 @@ int MODULEMAINFUNC (int argc, char** argv){ memset(&defparam.sincr, 0, sizeof(defparam.sincr)); if(isudp) while(!srv.fds.events)usleep(SLEEPTIME); } - + while(!conf.timetoexit && conf.version <= srv.version) usleep(SLEEPTIME); if(!srv.silent) srv.logfunc(&defparam, (unsigned char *)"Exiting thread"); if(fp) fclose(fp); From 7742b08ec5518316ce6220198f55bd17bf6329c0 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 7 Jun 2016 14:16:17 +0300 Subject: [PATCH 28/38] Revert "Delay service exit until new configuration is loaded" This reverts commit 05f39246bfd3599673d9e863c889861911065d61. --- src/proxymain.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/proxymain.c b/src/proxymain.c index 4aea520..d6c1a37 100644 --- a/src/proxymain.c +++ b/src/proxymain.c @@ -685,7 +685,7 @@ int MODULEMAINFUNC (int argc, char** argv){ memset(&defparam.sincr, 0, sizeof(defparam.sincr)); if(isudp) while(!srv.fds.events)usleep(SLEEPTIME); } - while(!conf.timetoexit && conf.version <= srv.version) usleep(SLEEPTIME); + if(!srv.silent) srv.logfunc(&defparam, (unsigned char *)"Exiting thread"); if(fp) fclose(fp); From cdc4210a0a87fff68a607d512c0e08cac32742cf Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 7 Jun 2016 14:16:55 +0300 Subject: [PATCH 29/38] Fix '%i' logging --- src/version.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/version.h b/src/version.h index fef05bd..4426d32 100644 --- a/src/version.h +++ b/src/version.h @@ -1,2 +1,2 @@ #define VERSION "3proxy-0.9-devel" -#define BUILDDATE "160228150442" +#define BUILDDATE "160518000524" From 6426ed0c1aeed21f95da4d59734a2e1bf73f9a1a Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 7 Jun 2016 15:39:14 +0300 Subject: [PATCH 30/38] fix %i logging --- src/common.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/common.c b/src/common.c index 854f5b2..b72cfb9 100644 --- a/src/common.c +++ b/src/common.c @@ -503,7 +503,7 @@ int dobuf2(struct clientparam * param, unsigned char * buf, const unsigned char i += myinet_ntop(*SAFAMILY(¶m->sinsl), SAADDR(¶m->sinsl), (char *)buf + i, 64); break; case 'i': - i += myinet_ntop(*SAFAMILY(¶m->sincl), SAADDR(¶m->sinsl), (char *)buf + i, 64); + i += myinet_ntop(*SAFAMILY(¶m->sincl), SAADDR(¶m->sincl), (char *)buf + i, 64); break; case 'C': i += myinet_ntop(*SAFAMILY(¶m->sincr), SAADDR(¶m->sincr), (char *)buf + i, 64); @@ -638,7 +638,8 @@ void logsyslog(struct clientparam * param, const unsigned char *s) { #endif int doconnect(struct clientparam * param){ - SASIZETYPE size = sizeof(param->sinsr); + SASIZETYPE size; + if (*SAFAMILY(¶m->sincr) == *SAFAMILY(¶m->req) && !memcmp(SAADDR(¶m->sincr), SAADDR(¶m->req), SAADDRLEN(¶m->req)) && *SAPORT(¶m->sincr) == *SAPORT(¶m->req)) return 519; @@ -646,6 +647,7 @@ int doconnect(struct clientparam * param){ if (param->operation == ADMIN || param->operation == DNSRESOLVE || param->operation == BIND || param->operation == UDPASSOC) return 0; if (param->remsock != INVALID_SOCKET){ + size = sizeof(param->sinsr); if(so._getpeername(param->remsock, (struct sockaddr *)¶m->sinsr, &size)==-1) {return (15);} } else { From 4e4f71712db29955c626b0dc544b80f96bc9b455 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 16 Aug 2016 15:21:02 +0300 Subject: [PATCH 31/38] Fix: 'extip' may fail with 9 error code --- src/auth.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/auth.c b/src/auth.c index 874bc34..86176f9 100644 --- a/src/auth.c +++ b/src/auth.c @@ -317,8 +317,8 @@ int handleredirect(struct clientparam * param, struct ace * acentry){ connected = 1; } - if(!connected) return 9; - return (redir)?clientnegotiate(redir, param, (struct sockaddr *)¶m->req):0; + if(!connected || !redir) return 0; + return clientnegotiate(redir, param, (struct sockaddr *)¶m->req); } int IPInentry(struct sockaddr *sa, struct iplist *ipentry){ From b242d6df8c2d0566fe29c191797590dd5264aa6e Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 23 Aug 2016 14:19:27 +0300 Subject: [PATCH 32/38] Fix daemonize in *nix --- src/common.c | 7 +++++++ src/proxy.h | 2 +- 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/src/common.c b/src/common.c index b72cfb9..b6f4b86 100644 --- a/src/common.c +++ b/src/common.c @@ -17,6 +17,13 @@ int randomizer = 1; #ifndef _WIN32 pthread_attr_t pa; + + + void daemonize(void){ + if(fork()) exit(0); + else setsid(); + } + #endif unsigned char **stringtable = NULL; diff --git a/src/proxy.h b/src/proxy.h index 061cfff..7a1c530 100644 --- a/src/proxy.h +++ b/src/proxy.h @@ -104,7 +104,7 @@ #define PTHREAD_STACK_MIN 32768 #define sockerror strerror #endif -#define daemonize() {if(fork())exit(0); else setsid();} +void daemonize(void); #define SLEEPTIME 1000 #ifndef O_BINARY #define O_BINARY 0 From e2b406f27bc3ba98d350846b8ead7274f4b831cd Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Tue, 23 Aug 2016 18:36:18 +0300 Subject: [PATCH 33/38] Addition al fix for Linux (glibc?) specific daemon problem --- src/common.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/common.c b/src/common.c index b6f4b86..ad08142 100644 --- a/src/common.c +++ b/src/common.c @@ -20,8 +20,11 @@ int randomizer = 1; void daemonize(void){ - if(fork()) exit(0); - else setsid(); + if(fork() > 0) { + usleep(SLEEPTIME); + _exit(0); + } + setsid(); } #endif From 4e96a6609315d42ee53fe2d690fa8c56e0c9c037 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Sun, 4 Sep 2016 15:10:45 +0300 Subject: [PATCH 34/38] fix authentication via reverse name --- src/proxy.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/proxy.h b/src/proxy.h index 7a1c530..9c1cdf7 100644 --- a/src/proxy.h +++ b/src/proxy.h @@ -188,7 +188,7 @@ unsigned bandlimitfunc(struct clientparam *param, unsigned nbytesin, unsigned nb int scanaddr(const unsigned char *s, unsigned long * ip, unsigned long * mask); int myinet_ntop(int af, void *src, char *dst, socklen_t size); extern struct nserver nservers[MAXNSERVERS]; -struct nserver authnserver; +extern struct nserver authnserver; unsigned long getip(unsigned char *name); unsigned long getip46(int family, unsigned char *name, struct sockaddr *sa); unsigned long myresolver(int, unsigned char *, unsigned char *); From 880255093aeea14cf82d67bee3527fba025272f9 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Sun, 4 Sep 2016 15:11:15 +0300 Subject: [PATCH 35/38] minor compilers compatibility issues --- src/datatypes.c | 4 +++- src/icqpr.c | 6 +++--- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/src/datatypes.c b/src/datatypes.c index d009671..0a87901 100644 --- a/src/datatypes.c +++ b/src/datatypes.c @@ -61,14 +61,16 @@ static void pr_ip(struct node *node, CBFUNC cbf, void*cb){ if(node->value)(*cbf)(cb, buf, myinet_ntop(AF_INET, node -> value, buf, 4)); } +#ifndef NOIPV6 static void pr_ip6(struct node *node, CBFUNC cbf, void*cb){ char buf[64]; if(node->value)(*cbf)(cb, buf, myinet_ntop(AF_INET6, node -> value, buf, 16)); } +#endif static void pr_sa(struct node *node, CBFUNC cbf, void*cb){ #ifdef NOIPV6 - if(node->value)return pr_ip(node, cbf, cb); + if(node->value)pr_ip(node, cbf, cb); #else char buf[64]; buf[0] = '['; diff --git a/src/icqpr.c b/src/icqpr.c index bd45687..34dd2d2 100644 --- a/src/icqpr.c +++ b/src/icqpr.c @@ -25,20 +25,20 @@ struct flap_header { unsigned char chan; unsigned short seq; unsigned short size; - char data[0]; + char data[1]; }; struct snack_header { unsigned family; unsigned short flags; unsigned id; - char data[0]; + char data[1]; }; struct tlv_header { unsigned short type; unsigned short size; - char data[0]; + char data[1]; }; From 98908236641f2ccae780b4fd82dfb9be4ac018d3 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Sun, 4 Sep 2016 15:33:20 +0300 Subject: [PATCH 36/38] fix signess warning --- src/conf.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/conf.c b/src/conf.c index 735a222..eb91fe7 100644 --- a/src/conf.c +++ b/src/conf.c @@ -318,7 +318,7 @@ static int h_log(int argc, unsigned char ** argv){ conf.logname = (unsigned char *)mystrdup((char *)argv[1]); fp = fopen((char *)dologname (tmpbuf, conf.logname, NULL, conf.logtype, conf.logtime), "a"); if(!fp){ - perror(tmpbuf); + perror((char *)tmpbuf); return 1; } else { From ec9d556707953cd9c2a91c483ac64693f56aafd5 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Sun, 4 Sep 2016 15:33:38 +0300 Subject: [PATCH 37/38] Add makefile for OpenWatcom 2.0 --- .gitignore | 1 + Makefile.watcom | 43 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 44 insertions(+) create mode 100644 Makefile.watcom diff --git a/.gitignore b/.gitignore index 3d7d005..76400a8 100644 --- a/.gitignore +++ b/.gitignore @@ -15,6 +15,7 @@ tmp/ *.swp *.o *.idb +*.err res version.c 3proxy.res diff --git a/Makefile.watcom b/Makefile.watcom new file mode 100644 index 0000000..dd44821 --- /dev/null +++ b/Makefile.watcom @@ -0,0 +1,43 @@ +# +# 3 proxy Makefile for Open Watcom 2 +# +# You can try to remove -DWITH_STD_MALLOC to CFLAGS to use optimized malloc +# libraries +# +# Add /DSAFESQL to CFLAGS if you are using poorely written/tested ODBC driver + +BUILDDIR = ../bin/ +CC = cl +CFLAGS = /nologo /MT /D "NOIPV6" /D "NODEBUG" /D "NOODBC" /D "MSVC" /D "WITH_STD_MALLOC" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /D "_WIN32" /c +COUT = /Fo +LN = link +LDFLAGS = /nologo /subsystem:console /incremental:no +DLFLAGS = /DLL +DLSUFFICS = .dll +LIBS = ws2_32.lib advapi32.lib user32.lib kernel32.lib +LIBSOLD = libeay32MT.lib ssleay32MT.lib +LIBSPREFIX = +LIBSSUFFIX = .lib +LIBEXT = .lib +LNOUT = /out: +EXESUFFICS = .exe +OBJSUFFICS = .obj +DEFINEOPTION = /D +COMPFILES = *.pch *.idb *.err +REMOVECOMMAND = del 2>NUL >NUL +TYPECOMMAND = type +COMPATLIBS = +MAKEFILE = Makefile.watcom +PLUGINS = utf8tocp1251 WindowsAuthentication TrafficPlugin StringsPlugin PCREPlugin +VERFILE = $(VERFILE) + +include Makefile.inc + +../3proxy.res: + rc /fo../3proxy.res ../3proxy.rc + +3proxyres.obj: ../3proxy.res + cvtres /out:3proxyres.obj ../3proxy.res + +allplugins: + call ../makeplugins.bat \ No newline at end of file From fd29e887c34d17dba2e98d1ce35ad619d88fc737 Mon Sep 17 00:00:00 2001 From: z3APA3A <3APA3A@3proxy.ru> Date: Sun, 4 Sep 2016 15:49:04 +0300 Subject: [PATCH 38/38] add optimization to watcom makefile --- Makefile.watcom | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile.watcom b/Makefile.watcom index dd44821..e58f2ce 100644 --- a/Makefile.watcom +++ b/Makefile.watcom @@ -8,7 +8,7 @@ BUILDDIR = ../bin/ CC = cl -CFLAGS = /nologo /MT /D "NOIPV6" /D "NODEBUG" /D "NOODBC" /D "MSVC" /D "WITH_STD_MALLOC" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /D "_WIN32" /c +CFLAGS = /nologo /Ox /MT /D "NOIPV6" /D "NODEBUG" /D "NOODBC" /D "MSVC" /D "WITH_STD_MALLOC" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /D "_WIN32" /c COUT = /Fo LN = link LDFLAGS = /nologo /subsystem:console /incremental:no