This commit is contained in:
Jack Halford 2017-08-25 19:17:46 +02:00
parent 2d46d00df8
commit c5a9ac9970
6 changed files with 207 additions and 98 deletions

View file

@ -33,6 +33,7 @@ OBJ_DIR = objs/
SRC_BASE = \
main.c\
nmap.c\
parser.c\
listener.c\
SRCS = $(addprefix $(SRC_DIR), $(SRC_BASE))

View file

@ -24,7 +24,6 @@
# include <netinet/ip.h>
# include <netinet/ip_icmp.h>
# include <netinet/if_ether.h>
# include <arpa/inet.h>
# include <pcap.h>
# include <sys/wait.h>
# include <pthread.h>
@ -36,8 +35,12 @@
# define SCAN_FIN (1 << 4)
# define SCAN_XMAS (1 << 5)
# define SCAN_UDP (1 << 6)
# define SCAN_MAX 7
typedef struct s_data t_data;
typedef struct s_host t_host;
typedef struct s_tcp_packet t_tcp_packet;
typedef enum e_port_status t_port_status;
struct s_data
{
@ -47,12 +50,46 @@ struct s_data
t_list *port;
int threads;
int scan;
int src_port;
};
/* enum e_scan_type */
/* { */
/* SCAN_SYN, */
/* SCAN_NULL, */
/* SCAN_ACK, */
/* SCAN_FIN, */
/* SCAN_XMAS, */
/* SCAN_UDP, */
/* }; */
enum e_port_status
{
OPEN,
FILTERED,
CLOSED,
UNFILTERED,
OPEN_FILTERED,
};
struct s_host
{
struct sockaddr_in *addr;
char *
char *node; // user inputed node (ip or dn)
char *dn; // ai_canonname
char ip[INET6_ADDRSTRLEN]; // readable ip address (4 or 6)
int sock_tcp;
int sock_udp;
int sock_icmp;
t_port_status results[USHRT_MAX + 1];
char scanning[USHRT_MAX + 1];
struct sockaddr *addr;
size_t addrlen;
};
struct s_tcp_packet
{
struct iphdr iph;
struct tcphdr tcph;
};
static t_cliopts g_opts[];
@ -60,4 +97,10 @@ static t_cliopts g_opts[];
void nmap(t_data *data);
void *nmap_listener(void *arg);
int nmap_get_host(char *node, t_data *data);
int nmap_get_file(char *opt_arg, t_data *data);
int nmap_get_ports(char *opt_arg, t_data *data);
int nmap_get_threads(char *opt_arg, t_data *data);
int nmap_get_scan(char *opt_arg, t_data *data);
#endif

View file

@ -8,7 +8,7 @@ static void packet_callback(u_char *tmp, const struct pcap_pkthdr *pkthdr, const
(void)tmp;
(void)pkthdr;
(void)packet;
printf("received packet !!!");
printf("received packet !!!\n");
}
void *nmap_listener(void *arg)
@ -30,7 +30,7 @@ void *nmap_listener(void *arg)
fprintf(stderr, "pcap_open_live: %s", errbuf);
exit(EXIT_FAILURE);
}
if (!(str = ft_str3join("host ", data->host, " and (tcp or icmp)")))
if (!(str = ft_str3join("host ", ((t_host*)data->host->content)->ip, " and (tcp or icmp)")))
{
exit(EXIT_FAILURE);
}

View file

@ -3,79 +3,6 @@
#define NMAP_USAGE1 " [--ip HOST] [--file FILE]"
#define NMAP_USAGE2 " [--ports PORTS] [--speedup [NOMBRE]] [--scan [TYPE]] HOST"
int nmap_get_host(char *opt_arg, t_data *data)
{
t_host *host;
host = opt_arg;
struct sockaddr_in *addr;
struct addrinfo *servinfo, hints;
char addrstr[INET_ADDRSTRLEN];
int sockfd;
memset (&hints, 0, sizeof (hints));
hints.ai_family = PF_UNSPEC;
hints.ai_socktype = SOCK_RAW;
hints.ai_flags = AI_CANONNAME;
if (getaddrinfo(host, NULL, &hints, &servinfo))
{
fprintf(stderr, "Failed to resolve \"%s\"\n", host);
return (1);
}
host->addr = (struct sockaddr_in*)servinfo->ai_addr;
inet_ntop(AF_INET, &(addr->sin_addr), addrstr, INET_ADDRSTRLEN);
host->addrstr = addrstr;
/* MUST DO AND rDNS search here */
/* printf("rDNS record for %s: %s\n", addrstr, DOMAIN NAME WITH RDNS); */
if ((sockfd = socket(AF_INET, SOCK_RAW, IPPROTO_TCP)) == -1)
perror("server: socket");
ft_lsteadd(&data->host, &host);
return (0);
}
/* int nmap_get_file(char *opt_arg, t_data *data) */
/* { */
/* } */
/* int nmap_get_ports(char *opt_arg, t_data *data) */
/* { */
/* } */
int nmap_get_threads(char *opt_arg, t_data *data)
{
data->threads = ft_atoi(opt_arg);
return (0);
}
int nmap_get_scan(char *opt_arg, t_data *data)
{
while (*opt_arg)
{
if (*opt_arg == 'T')
data->scan |= SCAN_TCP;
else if (*opt_arg == 'S')
data->scan |= SCAN_SYN;
else if (*opt_arg == 'N')
data->scan |= SCAN_NULL;
else if (*opt_arg == 'A')
data->scan |= SCAN_ACK;
else if (*opt_arg == 'F')
data->scan |= SCAN_FIN;
else if (*opt_arg == 'X')
data->scan |= SCAN_XMAS;
else if (*opt_arg == 'U')
data->scan |= SCAN_UDP;
else
return (1);
opt_arg++;
}
return (0);
}
static t_cliopts g_opts[] =
{
{'i', "ip", 0, 0, nmap_get_host, 0},
@ -86,7 +13,6 @@ static t_cliopts g_opts[] =
{0, 0, 0, 0, 0, 0},
};
int nmap_parse(int ac, char **av, t_data *data)
{
(void)ac;
@ -97,8 +23,8 @@ int nmap_parse(int ac, char **av, t_data *data)
if (cliopts_get(av, g_opts, data))
return (ft_perror("nmap"));
if (!data->host && data->av_data)
data->host = *data->av_data;
if (!data->host && data->av_data && data->av_data)
nmap_get_host(*data->av_data, data);
if (!data->scan)
data->scan = SCAN_TCP;
return (0);
@ -108,6 +34,12 @@ int main(int ac, char **av)
{
t_data data;
if (getuid() != 0)
{
fprintf(stderr, "You must have root privileges to use nmap!\n");
return(1);
}
if (nmap_parse(ac, av, &data))
{
printf("usage: nmap --help\n");
@ -115,6 +47,12 @@ int main(int ac, char **av)
exit(1);
}
if (reserve_port(&data.src_port))
{
fprintf(stderr, "couldn't reserve port\n");
exit(1);
}
pthread_t listener;
pthread_create(&listener, NULL, &nmap_listener, &data);
nmap(&data);

View file

@ -12,31 +12,67 @@
#include "nmap.h"
int nmap_scan_syn(int sockfd, struct addrinfo *p)
unsigned short cksum(void *b, int len)
{
if (connect(sockfd, p->ai_addr, p->ai_addrlen))
printf("connect failed");
else
printf("connect success");
unsigned short *buf = b;
unsigned int sum=0;
for (sum = 0; len > 1; len -= 2)
sum += *((unsigned short*)buf++);
if (len == 1)
sum += *(unsigned char*)buf;
sum = (sum >> 16) + (sum & 0xFFFF);
return (~(sum + (sum >> 16)));
}
int nmap_scan_tcp(t_data *data, struct iphdr *iph, t_host *host, int port)
{
t_tcp_packet packet;
packet.iph = *iph;
tcphdr_init(&packet.tcph);
packet.tcph.dest = htons(port);
packet.tcph.source = htons(data->src_port);
packet.tcph.syn = 1;
packet.tcph.check = cksum(&packet, sizeof(t_tcp_packet));
if (sendto(host->sock_tcp, &packet, sizeof(packet), 0, host->addr, host->addrlen) < 0)
{
perror("sendto");
exit(1);
}
printf("packet sent\n");
sleep(2);
return (0);
}
int nmap_scan(char *host, int port, int scan)
{
nmap_scan_syn(sockfd, servinfo);
freeaddrinfo(servinfo);
return (0);
}
/* int nmap_scan(char *host, int port, int scan) */
/* { */
/* (void)scan; */
/* nmap_scan_syn(sockfd, servinfo); */
/* return (0); */
/* } */
void nmap(t_data *data)
{
while (data->host)
t_list *list;
t_host *host;
struct iphdr iph;
list = data->host;
if (!list)
return ;
for (host = list->content; list != NULL; list = list->next )
{
nmap_scan(data->host, 80, SCAN_TCP);
printf("scanning %s...\n", host->dn);
iphdr_init(&iph);
iph.protocol = IPPROTO_TCP;
iph.daddr = *(int32_t*)host->addr;
iph.tot_len = sizeof(t_tcp_packet);
nmap_scan_tcp(data, &iph, host, 80);
break ;
}
}

91
nmap/srcs/parser.c Normal file
View file

@ -0,0 +1,91 @@
#include "nmap.h"
int nmap_get_host(char *node, t_data *data)
{
t_host host;
struct addrinfo *servinfo, hints;
memset (&hints, 0, sizeof (hints));
hints.ai_family = PF_UNSPEC;
hints.ai_socktype = SOCK_RAW;
hints.ai_flags = AI_CANONNAME;
if (getaddrinfo(node, NULL, &hints, &servinfo))
{
fprintf(stderr, "Failed to resolve \"%s\"\n", node);
return (1);
}
host.addr = servinfo->ai_addr;
host.addrlen = servinfo->ai_addrlen;
host.node = node;
host.dn = servinfo->ai_canonname;
void *addr;
if (servinfo->ai_family == AF_INET) { // IPv4
struct sockaddr_in *ipv4 = (struct sockaddr_in *)servinfo->ai_addr;
addr = &(ipv4->sin_addr);
} else { // IPv6
struct sockaddr_in6 *ipv6 = (struct sockaddr_in6 *)servinfo->ai_addr;
addr = &(ipv6->sin6_addr);
}
// convert the IP to a string and print it:
inet_ntop(servinfo->ai_family, addr, host.ip, sizeof(host.ip));
printf("dn=%s\n", host.dn);
printf("ip=%s\n", host.ip);
/* MUST DO AND rDNS search here */
/* printf("rDNS record for %s: %s\n", addrstr, DOMAIN NAME WITH RDNS); */
if ((host.sock_tcp = socket(AF_INET, SOCK_RAW, IPPROTO_TCP)) == -1)
perror("server: socket");
int val = 1;
if (setsockopt(host.sock_tcp, IPPROTO_IP, IP_HDRINCL, &val, sizeof(val)) == -1)
return (1);
ft_lsteadd(&data->host, ft_lstnew(&host, sizeof(host)));
return (0);
}
/* int nmap_get_file(char *opt_arg, t_data *data) */
/* { */
/* } */
/* int nmap_get_ports(char *opt_arg, t_data *data) */
/* { */
/* } */
int nmap_get_threads(char *opt_arg, t_data *data)
{
data->threads = ft_atoi(opt_arg);
return (0);
}
int nmap_get_scan(char *opt_arg, t_data *data)
{
while (*opt_arg)
{
if (*opt_arg == 'T')
data->scan |= SCAN_TCP;
else if (*opt_arg == 'S')
data->scan |= SCAN_SYN;
else if (*opt_arg == 'N')
data->scan |= SCAN_NULL;
else if (*opt_arg == 'A')
data->scan |= SCAN_ACK;
else if (*opt_arg == 'F')
data->scan |= SCAN_FIN;
else if (*opt_arg == 'X')
data->scan |= SCAN_XMAS;
else if (*opt_arg == 'U')
data->scan |= SCAN_UDP;
else
return (1);
opt_arg++;
}
return (0);
}