bind address for connect

This commit is contained in:
Vladimir Goncharov 2024-08-22 15:49:50 +07:00
parent a863c35ce3
commit c793ec8e1c
3 changed files with 51 additions and 8 deletions

View File

@ -72,6 +72,9 @@ struct params_s
bool tamper_start_n,tamper_cutoff_n; bool tamper_start_n,tamper_cutoff_n;
unsigned int tamper_start,tamper_cutoff; unsigned int tamper_start,tamper_cutoff;
struct sockaddr_in connect_bind4;
struct sockaddr_in6 connect_bind6;
int debug; int debug;
#if defined(BSD) #if defined(BSD)

View File

@ -138,6 +138,7 @@ static void exithelp(void)
" * multiple binds are supported. each bind-addr, bind-iface* start new bind\n" " * multiple binds are supported. each bind-addr, bind-iface* start new bind\n"
" --port=<port>\t\t\t\t; only one port number for all binds is supported\n" " --port=<port>\t\t\t\t; only one port number for all binds is supported\n"
" --socks\t\t\t\t; implement socks4/5 proxy instead of transparent proxy\n" " --socks\t\t\t\t; implement socks4/5 proxy instead of transparent proxy\n"
" --connect-bind-addr=<v4_addr>|<v6_addr> ; address for outbound connections\n"
" --no-resolve\t\t\t\t; disable socks5 remote dns ability\n" " --no-resolve\t\t\t\t; disable socks5 remote dns ability\n"
" --resolver-threads=<int>\t\t; number of resolver worker threads\n" " --resolver-threads=<int>\t\t; number of resolver worker threads\n"
" --local-rcvbuf=<bytes>\n" " --local-rcvbuf=<bytes>\n"
@ -355,13 +356,14 @@ void parse_params(int argc, char *argv[])
{ "skip-nodelay",no_argument,0,0 },// optidx=51 { "skip-nodelay",no_argument,0,0 },// optidx=51
{ "tamper-start",required_argument,0,0 },// optidx=52 { "tamper-start",required_argument,0,0 },// optidx=52
{ "tamper-cutoff",required_argument,0,0 },// optidx=53 { "tamper-cutoff",required_argument,0,0 },// optidx=53
{ "connect-bind-addr",required_argument,0,0 },// optidx=54
#if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__) #if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__)
{ "enable-pf",no_argument,0,0 },// optidx=54 { "enable-pf",no_argument,0,0 },// optidx=55
#elif defined(__linux__) #elif defined(__linux__)
{ "mss",required_argument,0,0 },// optidx=54 { "mss",required_argument,0,0 },// optidx=55
{ "mss-pf",required_argument,0,0 },// optidx=55 { "mss-pf",required_argument,0,0 },// optidx=56
#ifdef SPLICE_PRESENT #ifdef SPLICE_PRESENT
{ "nosplice",no_argument,0,0 },// optidx=55 { "nosplice",no_argument,0,0 },// optidx=57
#endif #endif
#endif #endif
{ "hostlist-auto-retrans-threshold",optional_argument,0,0}, // ignored. for nfqws command line compatibility { "hostlist-auto-retrans-threshold",optional_argument,0,0}, // ignored. for nfqws command line compatibility
@ -784,12 +786,29 @@ void parse_params(int argc, char *argv[])
params.tamper_cutoff = atoi(p); params.tamper_cutoff = atoi(p);
} }
break; break;
case 54: /* connect-bind-addr */
{
if (inet_pton(AF_INET, optarg, &params.connect_bind4.sin_addr))
{
params.connect_bind4.sin_family = AF_INET;
}
else if (inet_pton(AF_INET6, optarg, &params.connect_bind6.sin6_addr))
{
params.connect_bind6.sin6_family = AF_INET6;
}
else
{
fprintf(stderr, "bad bind addr : %s\n", optarg);
exit_clean(1);
}
}
break;
#if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__) #if defined(BSD) && !defined(__OpenBSD__) && !defined(__APPLE__)
case 54: /* enable-pf */ case 55: /* enable-pf */
params.pf_enable = true; params.pf_enable = true;
break; break;
#elif defined(__linux__) #elif defined(__linux__)
case 54: /* mss */ case 55: /* mss */
// this option does not work in any BSD and MacOS. OS may accept but it changes nothing // this option does not work in any BSD and MacOS. OS may accept but it changes nothing
params.mss = atoi(optarg); params.mss = atoi(optarg);
if (params.mss<88 || params.mss>32767) if (params.mss<88 || params.mss>32767)
@ -798,7 +817,7 @@ void parse_params(int argc, char *argv[])
exit_clean(1); exit_clean(1);
} }
break; break;
case 55: /* mss-pf */ case 56: /* mss-pf */
if (!pf_parse(optarg,&params.mss_pf)) if (!pf_parse(optarg,&params.mss_pf))
{ {
fprintf(stderr, "Invalid MSS port filter.\n"); fprintf(stderr, "Invalid MSS port filter.\n");
@ -806,7 +825,7 @@ void parse_params(int argc, char *argv[])
} }
break; break;
#ifdef SPLICE_PRESENT #ifdef SPLICE_PRESENT
case 56: /* nosplice */ case 57: /* nosplice */
params.nosplice = true; params.nosplice = true;
break; break;
#endif #endif

View File

@ -390,6 +390,27 @@ static int connect_remote(const struct sockaddr *remote_addr, bool bApplyConnect
VPRINT("Not setting MSS. Port %u is out of MSS port range.",port) VPRINT("Not setting MSS. Port %u is out of MSS port range.",port)
} }
} }
// if no bind address specified - address family will be 0 in params_connect_bindX
if(remote_addr->sa_family == params.connect_bind4.sin_family)
{
if (bind(remote_fd, (struct sockaddr *)&params.connect_bind4, sizeof(struct sockaddr_in)) == -1)
{
perror("bind on connect");
close(remote_fd);
return -1;
}
}
else if(remote_addr->sa_family == params.connect_bind6.sin6_family)
{
if (bind(remote_fd, (struct sockaddr *)&params.connect_bind6, sizeof(struct sockaddr_in6)) == -1)
{
perror("bind on connect");
close(remote_fd);
return -1;
}
}
if (connect(remote_fd, remote_addr, remote_addr->sa_family == AF_INET ? sizeof(struct sockaddr_in) : sizeof(struct sockaddr_in6)) < 0) if (connect(remote_fd, remote_addr, remote_addr->sa_family == AF_INET ? sizeof(struct sockaddr_in) : sizeof(struct sockaddr_in6)) < 0)
{ {
if(errno != EINPROGRESS) if(errno != EINPROGRESS)