forked from mirrors/tftp-hpa-google
Local port range functionality hack
This commit is contained in:
parent
25d63c415a
commit
ae1305e2d5
1 changed files with 43 additions and 10 deletions
|
@ -107,7 +107,8 @@ const char **dirs;
|
||||||
int secure = 0;
|
int secure = 0;
|
||||||
int cancreate = 0;
|
int cancreate = 0;
|
||||||
int unixperms = 0;
|
int unixperms = 0;
|
||||||
|
int portrange = 0;
|
||||||
|
unsigned int portrange_from, portrange_to;
|
||||||
int verbosity = 0;
|
int verbosity = 0;
|
||||||
|
|
||||||
struct formats;
|
struct formats;
|
||||||
|
@ -304,7 +305,9 @@ main(int argc, char **argv)
|
||||||
|
|
||||||
openlog(__progname, LOG_PID|LOG_NDELAY, LOG_DAEMON);
|
openlog(__progname, LOG_PID|LOG_NDELAY, LOG_DAEMON);
|
||||||
|
|
||||||
while ((c = getopt(argc, argv, "cspvVla:B:u:U:r:t:T:m:")) != -1)
|
srand(time(NULL) ^ getpid());
|
||||||
|
|
||||||
|
while ((c = getopt(argc, argv, "cspvVla:B:u:U:r:t:T:R:m:")) != -1)
|
||||||
switch (c) {
|
switch (c) {
|
||||||
case 'c':
|
case 'c':
|
||||||
cancreate = 1;
|
cancreate = 1;
|
||||||
|
@ -347,6 +350,16 @@ main(int argc, char **argv)
|
||||||
maxtimeout = rexmtval*TIMEOUT_LIMIT;
|
maxtimeout = rexmtval*TIMEOUT_LIMIT;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case 'R':
|
||||||
|
{
|
||||||
|
if ( sscanf(optarg, "%u:%u", &portrange_from, &portrange_to) != 2 ||
|
||||||
|
portrange_from > portrange_to || portrange_to >= 65535 ) {
|
||||||
|
syslog(LOG_ERR, "Bad port range: %s", optarg);
|
||||||
|
exit(EX_USAGE);
|
||||||
|
}
|
||||||
|
portrange = 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
case 'u':
|
case 'u':
|
||||||
user = optarg;
|
user = optarg;
|
||||||
break;
|
break;
|
||||||
|
@ -705,11 +718,31 @@ main(int argc, char **argv)
|
||||||
|
|
||||||
/* Process the request... */
|
/* Process the request... */
|
||||||
|
|
||||||
myaddr.sin_port = htons(0); /* We want a new local port */
|
while(1) {
|
||||||
|
unsigned int port;
|
||||||
|
|
||||||
|
if ( portrange ) {
|
||||||
|
/* Pick a (pseudo)random port in the relevant range */
|
||||||
|
port = portrange_from + rand() % (portrange_to-portrange_from+1);
|
||||||
|
} else {
|
||||||
|
port = 0; /* Let the kernel pick a port */
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
myaddr.sin_port = htons(port);
|
||||||
|
|
||||||
if (bind(peer, (struct sockaddr *)&myaddr, sizeof myaddr) < 0) {
|
if (bind(peer, (struct sockaddr *)&myaddr, sizeof myaddr) < 0) {
|
||||||
|
if ( (errno == EINVAL || errno == EADDRINUSE) && portrange )
|
||||||
|
continue; /* Should not happen in normal operation, but try again */
|
||||||
|
|
||||||
syslog(LOG_ERR, "bind: %m");
|
syslog(LOG_ERR, "bind: %m");
|
||||||
exit(EX_IOERR);
|
exit(EX_IOERR);
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
if (connect(peer, (struct sockaddr *)&from, sizeof from) < 0) {
|
if (connect(peer, (struct sockaddr *)&from, sizeof from) < 0) {
|
||||||
syslog(LOG_ERR, "connect: %m");
|
syslog(LOG_ERR, "connect: %m");
|
||||||
exit(EX_IOERR);
|
exit(EX_IOERR);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue