mirror of
https://github.com/nmap/nmap.git
synced 2025-12-17 21:19:01 +00:00
adding IPv6 support to RPC scan
This commit is contained in:
@@ -1,5 +1,9 @@
|
|||||||
# Nmap Changelog ($Id$); -*-text-*-
|
# Nmap Changelog ($Id$); -*-text-*-
|
||||||
|
|
||||||
|
o Added IPv6 host support to the RPC scan. Attempting this before
|
||||||
|
(via -sV) caused a segmentation fault. Thanks to Will Cladek for
|
||||||
|
the report. [Kris]
|
||||||
|
|
||||||
o We now escape newlines, carriage returns, and tabs (\n\r\t) in XML
|
o We now escape newlines, carriage returns, and tabs (\n\r\t) in XML
|
||||||
output. While those are allowed in XML attributes, they get
|
output. While those are allowed in XML attributes, they get
|
||||||
normalized which can make formatting the output difficult for
|
normalized which can make formatting the output difficult for
|
||||||
|
|||||||
@@ -479,7 +479,7 @@ void NmapOps::ValidateOptions() {
|
|||||||
fatal("--min-parallelism=%i must be less than or equal to --max-parallelism=%i",min_parallelism,max_parallelism);
|
fatal("--min-parallelism=%i must be less than or equal to --max-parallelism=%i",min_parallelism,max_parallelism);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (af() == AF_INET6 && (numdecoys|osscan|bouncescan|fragscan|ackscan|finscan|idlescan|ipprotscan|maimonscan|nullscan|rpcscan|synscan|udpscan|windowscan|xmasscan)) {
|
if (af() == AF_INET6 && (numdecoys|osscan|bouncescan|fragscan|ackscan|finscan|idlescan|ipprotscan|maimonscan|nullscan|synscan|udpscan|windowscan|xmasscan)) {
|
||||||
fatal("Sorry -- IPv6 support is currently only available for connect() scan (-sT), ping scan (-sP), and list scan (-sL). OS detection and decoys are also not supported with IPv6. Further support is under consideration.");
|
fatal("Sorry -- IPv6 support is currently only available for connect() scan (-sT), ping scan (-sP), and list scan (-sL). OS detection and decoys are also not supported with IPv6. Further support is under consideration.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
73
nmap_rpc.cc
73
nmap_rpc.cc
@@ -212,13 +212,17 @@ int get_rpc_procs(unsigned long **programs, unsigned long *num_programs) {
|
|||||||
/* Send an RPC query to the specified host/port on the specified protocol
|
/* Send an RPC query to the specified host/port on the specified protocol
|
||||||
looking for the specified RPC program. We cache our sending sockets
|
looking for the specified RPC program. We cache our sending sockets
|
||||||
to avoid recreating and (with TCP) reconnect()'ing them each time */
|
to avoid recreating and (with TCP) reconnect()'ing them each time */
|
||||||
int send_rpc_query(const struct in_addr *target_host, unsigned short portno,
|
int send_rpc_query(Target *target_host, unsigned short portno,
|
||||||
int ipproto, unsigned long program, int scan_offset,
|
int ipproto, unsigned long program, int scan_offset,
|
||||||
int trynum) {
|
int trynum) {
|
||||||
static struct in_addr last_target_host;
|
static struct sockaddr_storage last_target;
|
||||||
|
struct sockaddr_storage sock;
|
||||||
|
size_t socklen;
|
||||||
static int last_ipproto = -1;
|
static int last_ipproto = -1;
|
||||||
static unsigned short last_portno = 0;
|
struct sockaddr_in *sin = NULL, *lastsin = NULL;
|
||||||
struct sockaddr_in sock;
|
#ifdef HAVE_IPV6
|
||||||
|
struct sockaddr_in6 *sin6 = NULL, *lastsin6 = NULL;
|
||||||
|
#endif
|
||||||
char rpch_buf[256];
|
char rpch_buf[256];
|
||||||
struct rpc_hdr *rpch;
|
struct rpc_hdr *rpch;
|
||||||
int res, err = 0;
|
int res, err = 0;
|
||||||
@@ -238,38 +242,57 @@ int send_rpc_query(const struct in_addr *target_host, unsigned short portno,
|
|||||||
log_write(LOG_PLAIN, "Sending RPC probe for program %li to %hu/%s -- scan_offset=%d trynum=%d xid=%lX\n", program, portno, proto2ascii(ipproto), scan_offset, trynum, rpc_xid_base + ((portno & 0x3FFF) << 16) + (trynum << 30) + scan_offset);
|
log_write(LOG_PLAIN, "Sending RPC probe for program %li to %hu/%s -- scan_offset=%d trynum=%d xid=%lX\n", program, portno, proto2ascii(ipproto), scan_offset, trynum, rpc_xid_base + ((portno & 0x3FFF) << 16) + (trynum << 30) + scan_offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
memset(&sock, 0, sizeof(sock));
|
||||||
|
target_host->TargetSockAddr(&sock, &socklen);
|
||||||
|
|
||||||
|
if (sock.ss_family == AF_INET) {
|
||||||
|
sin = (struct sockaddr_in *) &sock;
|
||||||
|
lastsin = (struct sockaddr_in *) &last_target;
|
||||||
|
|
||||||
|
sin->sin_port = htons(portno);
|
||||||
|
}
|
||||||
|
#ifdef HAVE_IPV6
|
||||||
|
else {
|
||||||
|
sin6 = (struct sockaddr_in6 *) &sock;
|
||||||
|
lastsin6 = (struct sockaddr_in6 *) &last_target;
|
||||||
|
|
||||||
|
sin6->sin6_port = htons(portno);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/* First we check whether we have to create a new connection -- we
|
/* First we check whether we have to create a new connection -- we
|
||||||
need to if we have a new target_host, or a new portno, or the socket
|
need to if we have a new target_host, or a new portno, or the socket
|
||||||
we want to use is -1 */
|
we want to use is -1 */
|
||||||
if (ipproto == IPPROTO_TCP &&
|
if (ipproto == IPPROTO_TCP) {
|
||||||
(last_target_host.s_addr != target_host->s_addr ||
|
if ((sock.ss_family == AF_INET &&
|
||||||
last_portno != portno || last_ipproto != IPPROTO_TCP)) {
|
memcmp(sin, lastsin, sizeof(struct sockaddr_in)))
|
||||||
/* New host or port -- kill our old tcp socket */
|
#ifdef HAVE_IPV6
|
||||||
if (tcp_rpc_socket != -1) {
|
|| (sock.ss_family == AF_INET6 &&
|
||||||
close(tcp_rpc_socket);
|
memcmp(sin6, lastsin6, sizeof(struct sockaddr_in6)))
|
||||||
tcp_rpc_socket = -1;
|
#endif
|
||||||
tcp_readlen = 0;
|
|| last_ipproto != IPPROTO_TCP) {
|
||||||
|
/* New host or port -- kill our old tcp socket */
|
||||||
|
if (tcp_rpc_socket != -1) {
|
||||||
|
close(tcp_rpc_socket);
|
||||||
|
tcp_rpc_socket = -1;
|
||||||
|
tcp_readlen = 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
last_ipproto = ipproto;
|
|
||||||
last_target_host.s_addr = target_host->s_addr;
|
|
||||||
last_portno = portno;
|
|
||||||
|
|
||||||
memset(&sock, 0, sizeof(sock));
|
last_target = sock;
|
||||||
sock.sin_family = AF_INET;
|
last_ipproto = ipproto;
|
||||||
sock.sin_addr.s_addr = target_host->s_addr;
|
|
||||||
sock.sin_port = htons(portno);
|
|
||||||
|
|
||||||
if (ipproto == IPPROTO_TCP && tcp_rpc_socket == -1) {
|
if (ipproto == IPPROTO_TCP && tcp_rpc_socket == -1) {
|
||||||
if ((tcp_rpc_socket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1)
|
if ((tcp_rpc_socket = socket(sock.ss_family, SOCK_STREAM, IPPROTO_TCP)) == -1)
|
||||||
pfatal("Socket troubles in %s", __func__);
|
pfatal("Socket troubles in %s", __func__);
|
||||||
/* I should unblock the socket here and timeout the connect() */
|
/* I should unblock the socket here and timeout the connect() */
|
||||||
res = connect(tcp_rpc_socket, (struct sockaddr *) &sock,
|
res = connect(tcp_rpc_socket, (struct sockaddr *) &sock,
|
||||||
sizeof(struct sockaddr_in));
|
sizeof(struct sockaddr_storage));
|
||||||
if (res == -1) {
|
if (res == -1) {
|
||||||
if (o.debugging) {
|
if (o.debugging) {
|
||||||
gh_perror("Failed to connect to port %d of %s in %s",
|
gh_perror("Failed to connect to port %d of %s in %s",
|
||||||
portno, inet_ntoa(*target_host), __func__);
|
portno, target_host->targetipstr(), __func__);
|
||||||
}
|
}
|
||||||
close(tcp_rpc_socket);
|
close(tcp_rpc_socket);
|
||||||
tcp_rpc_socket = -1;
|
tcp_rpc_socket = -1;
|
||||||
@@ -277,7 +300,7 @@ int send_rpc_query(const struct in_addr *target_host, unsigned short portno,
|
|||||||
}
|
}
|
||||||
unblock_socket(tcp_rpc_socket);
|
unblock_socket(tcp_rpc_socket);
|
||||||
} else if (ipproto == IPPROTO_UDP && udp_rpc_socket == -1) {
|
} else if (ipproto == IPPROTO_UDP && udp_rpc_socket == -1) {
|
||||||
if ((udp_rpc_socket = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
|
if ((udp_rpc_socket = socket(sock.ss_family, SOCK_DGRAM, 0)) == -1)
|
||||||
pfatal("UDP socket troubles in %s", __func__);
|
pfatal("UDP socket troubles in %s", __func__);
|
||||||
unblock_socket(udp_rpc_socket);
|
unblock_socket(udp_rpc_socket);
|
||||||
}
|
}
|
||||||
@@ -306,7 +329,7 @@ int send_rpc_query(const struct in_addr *target_host, unsigned short portno,
|
|||||||
if (o.debugging > 1)
|
if (o.debugging > 1)
|
||||||
hdump((unsigned char *) rpch, sizeof(struct rpc_hdr));
|
hdump((unsigned char *) rpch, sizeof(struct rpc_hdr));
|
||||||
res = sendto(udp_rpc_socket, (char *)rpch, sizeof(struct rpc_hdr), 0,
|
res = sendto(udp_rpc_socket, (char *)rpch, sizeof(struct rpc_hdr), 0,
|
||||||
(struct sockaddr *) &sock, sizeof(struct sockaddr_in));
|
(struct sockaddr *) &sock, sizeof(struct sockaddr_storage));
|
||||||
if (res == -1)
|
if (res == -1)
|
||||||
err = socket_errno();
|
err = socket_errno();
|
||||||
} while(res == -1 && (err == EINTR || err == ENOBUFS));
|
} while(res == -1 && (err == EINTR || err == ENOBUFS));
|
||||||
|
|||||||
@@ -176,7 +176,7 @@ struct rpcscaninfo {
|
|||||||
|
|
||||||
int get_rpc_procs(unsigned long **programs, unsigned long *num_programs);
|
int get_rpc_procs(unsigned long **programs, unsigned long *num_programs);
|
||||||
char *nmap_getrpcnamebynum(unsigned long num);
|
char *nmap_getrpcnamebynum(unsigned long num);
|
||||||
int send_rpc_query(const struct in_addr *target_host, unsigned short portno,
|
int send_rpc_query(Target *target_host, unsigned short portno,
|
||||||
int ipproto, unsigned long program, int scan_offset,
|
int ipproto, unsigned long program, int scan_offset,
|
||||||
int trynum);
|
int trynum);
|
||||||
void get_rpc_results(Target *target, struct portinfo *scan,
|
void get_rpc_results(Target *target, struct portinfo *scan,
|
||||||
|
|||||||
@@ -5098,7 +5098,7 @@ void pos_scan(Target *target, u16 *portarray, int numports, stype scantype) {
|
|||||||
current->trynum++;
|
current->trynum++;
|
||||||
gettimeofday(¤t->sent[current->trynum], NULL);
|
gettimeofday(¤t->sent[current->trynum], NULL);
|
||||||
now = current->sent[current->trynum];
|
now = current->sent[current->trynum];
|
||||||
if (send_rpc_query(target->v4hostip(), rsi.rpc_current_port->portno,
|
if (send_rpc_query(target, rsi.rpc_current_port->portno,
|
||||||
rsi.rpc_current_port->proto,
|
rsi.rpc_current_port->proto,
|
||||||
current->portno, current - scan,
|
current->portno, current - scan,
|
||||||
current->trynum) == -1) {
|
current->trynum) == -1) {
|
||||||
@@ -5126,7 +5126,7 @@ void pos_scan(Target *target, u16 *portarray, int numports, stype scantype) {
|
|||||||
/* if (!testinglist) testinglist = current; */
|
/* if (!testinglist) testinglist = current; */
|
||||||
ss.numqueries_outstanding++;
|
ss.numqueries_outstanding++;
|
||||||
gettimeofday(¤t->sent[0], NULL);
|
gettimeofday(¤t->sent[0], NULL);
|
||||||
if (send_rpc_query(target->v4hostip(),
|
if (send_rpc_query(target,
|
||||||
rsi.rpc_current_port->portno,
|
rsi.rpc_current_port->portno,
|
||||||
rsi.rpc_current_port->proto, current->portno,
|
rsi.rpc_current_port->proto, current->portno,
|
||||||
current - scan, current->trynum) == -1) {
|
current - scan, current->trynum) == -1) {
|
||||||
|
|||||||
Reference in New Issue
Block a user